Sitemap

Thursday, June 25, 2015

Java: Input and Output streams

java.io package provides I/O classes to manipulate streams. This package supports two types of streams:
1. binary streams which handle binary data. InputStream and OutputStream are high level interfaces for manipulating binary streams.
2. character streams which handle character data. Reader and Writer are high level interfaces for manipulating character streams. In this section, the main focus is on binary streams.

By default, most of the streams read or write one byte at a time. This causes poor I/O performance because it takes lot of time to read/write byte by byte when dealing with large amounts of data. I/O provides Buffered streams to override this byte by byte default behaviors.



import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

public class Main {

    private static final String SOURCE_FILE = "D:\\test.jar";

    public static void main(String[] args) {
        Main io = new Main();
        try {
            long startTime = System.currentTimeMillis();
            io.readWrite(SOURCE_FILE, "D:\\test1.jar");
            long endTime = System.currentTimeMillis();
            System.out.println("Time taken for reading and writing using default behaviour : " + (endTime - startTime) +
                               " milli seconds");

            long startTime1 = System.currentTimeMillis();
            io.readWriteBuffer(SOURCE_FILE, "D:\\test2.jar");
            long endTime1 = System.currentTimeMillis();
            System.out.println("Time taken for reading and writing using buffered streams : " +
                               (endTime1 - startTime1) + " milli seconds");

            long startTime2 = System.currentTimeMillis();
            io.readWriteArray(SOURCE_FILE, "D:\\test3.jar");
            long endTime2 = System.currentTimeMillis();
            System.out.println("Time taken for reading and writing using custom buffering : " +
                               (endTime2 - startTime2) + " milli seconds");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public static void readWrite(String fileFrom, String fileTo) throws IOException {
        InputStream in = null;
        OutputStream out = null;
        try {
            in = new FileInputStream(fileFrom);
            out = new FileOutputStream(fileTo);
            while (true) {
                int bytedata = in.read();
                if (bytedata == -1)
                    break;
                out.write(bytedata);
            }
        } finally {
            if (in != null)
                in.close();
            if (out != null)
                out.close();
        }
    }

    public static void readWriteBuffer(String fileFrom, String fileTo) throws IOException {
        InputStream inBuffer = null;
        OutputStream outBuffer = null;
        try {
            InputStream in = new FileInputStream(fileFrom);
            inBuffer = new BufferedInputStream(in);
            OutputStream out = new FileOutputStream(fileTo);
            outBuffer = new BufferedOutputStream(out);
            while (true) {
                int bytedata = inBuffer.read();
                if (bytedata == -1)
                    break;
                out.write(bytedata);
            }
        } finally {
            if (inBuffer != null)
                inBuffer.close();
            if (outBuffer != null)
                outBuffer.close();
        }
    }

    public static void readWriteArray(String fileFrom, String fileTo) throws IOException {
        InputStream in = null;
        OutputStream out = null;
        try {
            in = new FileInputStream(fileFrom);
            out = new FileOutputStream(fileTo);
            int availableLength = in.available();
            byte[] totalBytes = new byte[availableLength];
            int bytedata = in.read(totalBytes);
            out.write(totalBytes);

        } finally {
            if (in != null)
                in.close();
            if (out != null)
                out.close();
        }
    }
}


OUTPUT
Time taken for reading and writing using default behaviour : 5188 milli seconds
Time taken for reading and writing using buffered streams : 3105 milli seconds
Time taken for reading and writing using custom buffering : 7 milli seconds

Java: Properties Class

A Properties object is a persistent Hashtable that stores key–value pairs of Strings. By "persistent", we mean that the Properties object can be written to an output stream (possibly a file) and read back in through an input stream. A common use of Properties objects in prior versions of Java was to maintain application-configuration data or user preferences for applications.

import java.io.FileOutputStream;
import java.io.FileInputStream;
import java.io.IOException;

import java.util.Properties;
import java.util.Set;

public class PropertiesTest {
    public static void main(String[] args) {
        Properties table = new Properties();

        // set properties
        table.setProperty("color", "blue");
        table.setProperty("width", "200");

        System.out.println("After setting properties");
        listProperties(table);

        // replace property value
        table.setProperty("color", "red");

        System.out.println("After replacing properties");
        listProperties(table);

        saveProperties(table);

        table.clear(); // empty table

        System.out.println("After clearing properties");
        listProperties(table);

        loadProperties(table);

        // get value of property color
        Object value = table.getProperty("color");

        // check if value is in table
        if (value != null)
            System.out.printf("Property color's value is %s%n", value);
        else
            System.out.println("Property color is not in table");
    }

    // save properties to a file

    private static void saveProperties(Properties props) {
        // save contents of table
        try {
            FileOutputStream output = new FileOutputStream("props.dat");
            props.store(output, "Sample Properties"); // save properties
            output.close();
            System.out.println("After saving properties");
            listProperties(props);
        } catch (IOException ioException) {
            ioException.printStackTrace();
        }
    }

    // load properties from a file

    private static void loadProperties(Properties props) {
        // load contents of table
        try {
            FileInputStream input = new FileInputStream("props.dat");
            props.load(input); // load properties
            input.close();
            System.out.println("After loading properties");
            listProperties(props);
        } catch (IOException ioException) {
            ioException.printStackTrace();
        }
    }

    // output property values

    private static void listProperties(Properties props) {
        Set<object> keys = props.keySet(); // get property names

        // output name/value pairs
        for (Object key : keys)
            System.out.printf("%s\t%s%n", key, props.getProperty((String)key));

        System.out.println();
    }
}


OUTPUT
After setting properties
color blue
width 200

After replacing properties
color red
width 200

After saving properties
color red
width 200

After clearing properties

After loading properties
color red
width 200

Property color's value is red


Java: Apache Ant

build.properties
src.dir=src
classes.dir=classes
main-class=com.mypkg.PortfolioManager
lib.dir=lib
docs.dir=docs
projectName=AntTutorial

build.xml
<?xml version="1.0" encoding="windows-1252" ?>
<!--Ant buildfile generated by Oracle JDeveloper-->
<!--Generated Apr 20, 2015 4:09:46 PM-->
<project xmlns="antlib:org.apache.tools.ant" name="Project" default="all" basedir=".">
  <property file="build.properties"/>

  <target name="clean">
    <delete dir="${classes.dir}"/>
    <delete dir="${docs.dir}"/>
  </target>

  <target name="init">
    <mkdir dir="${classes.dir}"/>
    <!--<mkdir dir="${docs.dir}"/>-->
  </target>

  <path id="classpath">
    <fileset dir="${lib.dir}" includes="**/*.jar"/>
  </path>

  <target name="compile" depends="init">
    <javac srcdir="${src.dir}" destdir="${classes.dir}" classpathref="classpath"/>
  </target>

  <!--<target name="docs" depends="compile">
    <javadoc packagenames="src" sourcepath="${src.dir}" destdir="${docs.dir}">
       <fileset dir="${src.dir}">
                <include name="**" />
           </fileset>
    </javadoc>
  </target>-->

  <target name="jar" depends="compile">
    <jar destfile="${projectName}.jar" basedir="${classes.dir}">
      <manifest>
        <attribute name="Main-Class" value="${main-class}"/>
      </manifest>
    </jar>
  </target>

  <target name="main" depends="clean,compile,jar"/>
</project>

Download the sample project from the file cabinet: AntTut.zip
More Info: http://www.tutorialspoint.com/ant/index.htm

Java: Dynamic Polymorphism

Polymorphism in Java has two types:
1. Compile time polymorphism (static binding)
2. Runtime polymorphism (dynamic binding).

Method overloading is an example of static polymorphism, while method overriding is an example of dynamic polymorphism.

public class Vehicle {
    public void move() {
        System.out.println("Vehicles can move!");
    }
}

class MotorBike extends Vehicle{
    public void move(){
    System.out.println("MotorBike can move and accelerate too!");
    }
}

class Test{
    public static void main(String[] args) {
        Vehicle vh = new MotorBike();
        vh.move(); // prints MotorBike can move and accelerate too!
        vh = new Vehicle();
        vh.move(); // prints Vehicles can move!
    }
}

It should be noted that in the first call to move(), the reference type is Vehicle and the object being referenced is MotorBike. So, when a call to move() is made, Java waits until runtime to determine which object is actually being pointed to by the reference.  In this case, the object is of the class MotorBike. So, the move() method of MotorBike class will be called. In the second call to move(), the object is of the class Vehicle. So, the move() method of Vehicle will be called.

More Info: http://www.javatpoint.com/static-binding-and-dynamic-binding
Info on typecasting: http://www.c4learn.com/java/java-type-casting-inheritance/

Java: Interfaces


public interface Language {
    String getBirthday();

    String getGreeting();
}

public class Indonesian implements Language {
    public String getBirthday() {
        return "Selamat Ulang Tahun";
    }

    public String getGreeting() {
        return "Apa kabar?";
    }
}

public class English implements Language {
    public String getBirthday() {
        return "Happy Birthday";
    }

    public String getGreeting() {
        return "How are you?";
    }
}

public class LanguageDemo {
    public static void main(String[] args) {
        Language language = new English();
        System.out.println(language.getBirthday());
        System.out.println(language.getGreeting());

        language = new Indonesian();
        System.out.println(language.getBirthday());
        System.out.println(language.getGreeting());
    }
}



OUTPUT:
Happy Birthday
How are you?
Selamat Ulang Tahun
Apa kabar?


Java: Decompiling using Procyon

import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;

import java.nio.file.FileSystems;
import java.nio.file.FileVisitResult;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.SimpleFileVisitor;
import java.nio.file.attribute.BasicFileAttributes;

import java.util.ArrayList;
import java.util.List;

public class ProcyonDecompiler {

    private static String JAR_DIRECTORY = "C:\\ucm";
    private static String DECOMPILER_FILEPATH = "lib/procyon-decompiler-0.5.29.jar";
    private static List<Path> fileList = new ArrayList<Path>();

    public static void main(String[] args) throws IOException, InterruptedException {
        walkDirectory();
        for (int i = 0; i < fileList.size(); i++) {
            Path absolutePath = fileList.get(i).toAbsolutePath();
            Path parentPath = fileList.get(i).getParent();
            Path fileName = fileList.get(i).getFileName();
            executeJarFile(absolutePath.toString(), parentPath.toString(), trimFileExtension(fileName.toString()));
        }
    }

    private static void executeJarFile(String absolutePath, String parentPath, String filename) throws IOException,
                                                                                                       InterruptedException {
        ProcessBuilder pb =
            new ProcessBuilder("java", "-jar", DECOMPILER_FILEPATH, "-jar", absolutePath, "-o",
                               parentPath + File.separator + filename);
        Process p = pb.start();
        BufferedReader in = new BufferedReader(new InputStreamReader(p.getInputStream()));
        String s = "";
        while ((s = in.readLine()) != null) {
            System.out.println(s);
        }
        int status = p.waitFor();
        System.out.println("Exited with status: " + status);
    }

    private static String trimFileExtension(String filename) {
        int pos = filename.lastIndexOf(".");
        if (pos > 0) {
            filename = filename.substring(0, pos);
        }
        return filename;
    }

    public static void walkDirectory() throws IOException {
        Path start = FileSystems.getDefault().getPath(JAR_DIRECTORY);
        Files.walkFileTree(start, new SimpleFileVisitor<Path>() {
            @Override
            public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
                if (file.toString().endsWith(".jar")) {
                    //System.out.println(file);
                    fileList.add(file);
                }
                return FileVisitResult.CONTINUE;
            }
        });
    }
}

Java: Extract a JAR file

import java.io.IOException;

import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;

import java.util.Enumeration;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;

public class UnzipJar {

    private static final String JAR_PATH = "D:\\test\\Java_gpl_v1.04.jar";

    public static void unzipJarFile(Path jar) throws IOException {
        if (!Files.exists(jar))
            return;

        String fnJar = jar.getFileName().toString();
        String fn = fnJar.substring(0, fnJar.lastIndexOf(".jar"));
        System.out.println(fnJar + " " + fn);
        Path dst = jar.getParent().resolve(fn);
        Files.createDirectory(dst);
        JarFile jf = new JarFile(jar.toString());

        //create directory
        for (Enumeration<JarEntry> enums = jf.entries(); enums.hasMoreElements();) {
            JarEntry entry = enums.nextElement();
            if (entry.isDirectory()) {
                Files.createDirectories(dst.resolve(entry.getName()));
            }
        }
        //copy file
        for (Enumeration<JarEntry> enums = jf.entries(); enums.hasMoreElements();) {
            JarEntry entry = enums.nextElement();
            if (!entry.isDirectory()) {
                Files.copy(jf.getInputStream(entry), dst.resolve(entry.getName()), StandardCopyOption.REPLACE_EXISTING);
            }
        }
    }

    public static void main(String[] args) throws IOException {
        unzipJarFile(Paths.get(JAR_PATH));
    }
}