SringSring

Sunday, 26 July 2015

Java 1.7 features

'Java latest changes' or' 'Java 1.7 changes' are covered in this topic. Java 1.7 [ Dolphin] is major update after java 1.5 tiger release. It is done on 2011-07-28 after around 5 years of java release 1.6 [Mustang]. These are major changes in java 1.7 release and most important is definitely 'Auto closeable' of resources.

1) Autocloseable Try Statement defining Resources – Java 1.7 introduces all new try-with-resources statement using which declaration and initialization of one or more resources can happen. But only the resources that implement the interface “java.lang.AutoCloseable” can be declared. Example:
      try (BufferedReader bufferedReader = new BufferedReader( FileReader(path)))
         {             return bufferedReader.readLine();  
         }
  In this code snippet, sampleBufferedReader instance is created within the try statement. Note that the example does not include a finally block that contains a code to close sampleBufferedReader as in Java 1.6 or earlier versions. Java 1.7 automatically closes the resources that are instantiated within the try-with-resources statement as shown above.

2) Catch Block Handling Multiple Exceptions – In Java 1.5 and Java 1.6, a catch block can handle only one type of exception. But in Java 1.7 and later versions, a single catch block can handle multiple exceptions. Here is an example showing catch blocks in Java 1.6:
     try {    }
      catch(SQLException exp1)
      {     throw exp1;    }
       catch(IOException exp2)
       {    throw exp2;   }
The same code snippet can be modified in Java 1.7 as:
      try  {….      }
      catch(SQLException | IOException |ArrayIndexOutofBoundsException exp1)
      {     throw exp1;   }

3) String Object as Expression in Switch Statement – So far only integral types are used as expressions in switch statement. But Java 1.7 permits usage of String object as a valid expression. Example:
   example:           
                            case "CASE1":
                                     System.out.println(“CASE1”);
                                     break;

4) JDBC in Java 1.7
JDBC contained in Java 1.7 / Java SE 7 is JDBC 4.1 that is newly getting introduced. JDBC 4.1 is more efficient when compared to JDBC 4.0.

5) Language Enhancements in JDBC 1.7
Java 1.7 introduces many language enhancements:

  Integral Types as Binary Literals – In Java 1.7 / Java SE 7, the integral types namely byte, short, int and long can also be expressed with the binary number system. To specify these integral types as binary literals, add the prefix 0B or 0b to number. For example, here is a byte literal represented as 8-bit binary number:
     byte sampleByte = (byte)0b01001101;
   
  Underscores Between Digits in Numeric Literal – In Java 1.7 and all later versions, “_” can be used in-between digits in any numeric literal. “_” can be used to group the digits similar to what “,” does when a bigger number is specified. But “_” can be specified only between digits and not in the beginning or end of the number. Example:
long NUMBER = 444_67_3459L;
In this example, the switch expression contains a string called sampleString.  The value of this string is matched with every case label and when the string content matches with case label then the corresponding case gets executed. 

  Automatic Type Inference during the Generic Instance Creation – In Java 1.7 while creating a generic instance, empty parameters namely <> can be specified instead of specifying the exact type arguments. However, this is permitted only in cases where the compiler can infer the appropriate type arguments. For example, in Java 1.7 you can specify:
      sampleMap = new HashMap<>();
Thus HashMap<> can be specified instead of HashMap>;. This <>; empty parameters of Java 1.7 are named as diamond operator.

6) Suppress Warnings - When declaring varargs method that includes parameterized types, if the body of the varargs method does not throw any exceptions like ClassCastException (which occurs due to improper handling of the varargs formal parameter) then the warnings can be suppressed in Java 1.7 by three different ways: 
(1) Add annotation @SafeVarargs to static method declarations and non constructor method declarations 
(2) Add annotation @SuppressWarnings({"unchecked", "varargs"}) to varargs method declaration 
(3) Directly use compiler option “-Xlint:varargs.
By suppressing the warnings in varargs method, occurrence of unchecked warnings can be prevented at compile time thus preventing Heap Pollution.

7) Java Virtual Machine Enhancements in Java 1.7
Java SE 7 / Java 1.7 newly introduce a JVM instruction called “invokedynamic” instruction.  Using “invokedynamic” instruction, the dynamic types programming language implementation becomes simpler. Thus Java 1.7 enables JVM support for the non-java languages.  

JAVA 1.5 features

JAVA 1.5 features | update Java 7 features


This Blog covers these topics: Java 1.5 interview questions / Java 1.5 updates / Java 1.7 updates. These are main changes in java 1.5 [ Tiger Release ] and these details are taken from SUN publication on jdk 1.5.

JAVA 1.5 New Features:
In Summary:
1) Generics
2) Enhanced For Loop
3) Autoboxing / Unboxing
4) Enums
5) Varags
6) Static Import
7) Metadata / Annotations
8) Garbage Collectors
9) Java Concurrent package

Worth reading java 1.7 changes to confirm that you are up-to-date for java changes.
Details of each change in java 1.5-
Generics
This long-awaited enhancement to the type system allows a type or method to operate on objects of various types while providing compile-time type safety. It adds compile-time type safety to the Collections Framework and eliminates the drudgery of casting. Refer to JSR 14.
      Generics provides a way for you to communicate the type of a collection to the compiler, so that it can be checked. Once the compiler knows the element type of the collection, the compiler can check that you have used the collection consistently and can insert the correct casts on values being taken out of the collection.
Example
static void expurgate(Collection; c) {
    for (Iterator; i = c.iterator(); i.hasNext(); )
      if (i.next().length() == 4)
        i.remove();
}
  The java.util.Collections class has been outfitted with wrapper classes that provide guaranteed run-time type safety. They are similar in structure to the synchronized and unmodifiable wrappers. These “checked collection wrappers” are very useful for debugging. Suppose you have a set of strings, s, into which some legacy code is mysteriously inserting an integer. Without the wrapper, you will not find out about the problem until you read the problem element from the set, and an automatically generated cast to String fails. At this point, it is too late to determine the source of the problem. If, however, you replace the declaration:
    Set s = new HashSet();

Enhanced for Loop
This new language construct eliminates the drudgery and error-proneness of iterators and index variables when iterating over collections and arrays. Refer to JSR 201 .
   Iterating over a collection is uglier than it needs to be. Consider the following method, which takes a collection of timer tasks and cancels them:
void cancelAll(Collection; c) {
    for (Iterator; i = c.iterator(); i.hasNext(); )
        i.next().cancel();
       }
   The iterator is just clutter. Furthermore, it is an opportunity for error. The iterator variable occurs three times in each loop: that is two chances to get it wrong. The for-each construct gets rid of the clutter and the opportunity for error. Here is how the example looks with the for-each construct:
void cancelAll(Collection ; c) {
    for (TimerTask t : c)
        t.cancel();
  }  When you see the colon (:) read it as “in.” The loop above reads as “for each TimerTask t in c.” As you can see, the for-each construct combines beautifully with generics. It preserves all of the type safety, while removing the remaining clutter. Because you don't have to declare the iterator, you don't have to provide a generic declaration for it. (The compiler does this for you behind your back, but you need not concern yourself with it.

Autoboxing/Unboxing
This facility eliminates the drudgery of manual conversion between primitive types (such as int) and wrapper types (such as Integer). Refer to JSR 201 .
   As any Java programmer knows, you can’t put an int (or other primitive value) into a collection. Collections can only hold object references, so you have to box primitive values into the appropriate wrapper class (which is Integer in the case of int). When you take the object out of the collection, you get the Integer that you put in; if you need an int, you must unbox the Integer using the intValue method. All of this boxing and unboxing is a pain, and clutters up your code. The autoboxing and unboxing feature automates the process, eliminating the pain and the clutter.
   The following example illustrates autoboxing and unboxing, along with generics and the for-each loop. In a mere ten lines of code, it computes and prints an alphabetized frequency table of the words appearing on the command line.
 import java.util.*;
// Prints a frequency table of the words on the command line
public class Frequency {
   public static void main(String[] args) {
      Map m = new TreeMap();
      for (String word : args) {
          Integer freq = m.get(word);
          m.put(word, (freq == null ? 1 : freq + 1));
      }
      System.out.println(m);
  }
}
java Frequency if it is to be it is up to me to do the watusi
{be=1, do=1, if=1, is=2, it=2, me=1, the=1, to=3, up=1, watusi=1}

Typesafe Enums   This flexible object-oriented enumerated type facility allows you to create enumerated types with arbitrary methods and fields. It provides all the benefits of the Typesafe Enum pattern ("Effective Java," Item 21) without the verbosity and the error-proneness. Refer to JSR 201.
In prior releases, the standard way to represent an enumerated type was the int Enum pattern:
// int Enum Pattern - has severe problems!
public static final int SEASON_WINTER = 0;
public static final int SEASON_SPRING = 1;
public static final int SEASON_SUMMER = 2;
public static final int SEASON_FALL   = 3;
This pattern has many problems, such as:
  • Not typesafe - Since a season is just an int you can pass in any other int value where a season is required, or add two seasons together (which makes no sense).
  • No namespace - You must prefix constants of an int enum with a string (in this case SEASON_) to avoid collisions with other int enum types.
  • Brittleness - Because int enums are compile-time constants, they are compiled into clients that use them. If a new constant is added between two existing constants or the order is changed, clients must be recompiled. If they are not, they will still run, but their behavior will be undefined.
  • Printed values are uninformative - Because they are just ints, if you print one out all      you get is a number, which tells you nothing about what it represents, or even what type it is.
     It is possible to get around these problems by using the Typesafe Enum pattern (see Effective Java Item 21), but this pattern has its own problems: It is quite verbose, hence error prone, and its enum constants cannot be used in switch statements.
    In 5.0, the Java™ programming language gets linguistic support for enumerated types. In their simplest form, these enums look just like their C, C++, and C# counterparts:
      enum Season { WINTER, SPRING, SUMMER, FALL }
 All enums implicitly extend java.lang.Enum. Since Java does not support multiple inheritance, an enum cannot extend anything else. The constructor for an enum type must be package-private or private access. It automatically creates the constants that are defined at the beginning of the enum body. You cannot invoke an enum constructor yourself.

Varargs
  This facility eliminates the need for manually boxing up argument lists into an array when invoking methods that accept variable-length argument lists. Refer to JSR 201.
   In past releases, a method that took an arbitrary number of values required you to create an array and put the values into the array prior to invoking the method. For example, here is how one used the MessageFormat class to format a message:
Object[] arguments = {
    new Integer(7),
    new Date(),
    "a disturbance in the Force"
};
String result = MessageFormat.format(
    "At {1,time} on {1,date}, there was {2} on planet "
     + "{0,number,integer}.", arguments);
   It is still true that multiple arguments must be passed in an array, but the varargs feature automates and hides the process. Furthermore, it is upward compatible with preexisting APIs. So, for example, the MessageFormat.format method now has this declaration:
    public static String format(String pattern, Object... arguments);

Static Import
  This facility lets you avoid qualifying static members with class names without the shortcomings of the "Constant Interface antipattern." Refer to JSR 201.
  In order to access static members, it is necessary to qualify references with the class they came from. For example, one must say:
         double r = Math.cos(Math.PI * theta);
  In order to get around this, people sometimes put static members into an interface and inherit from that interface. This is a bad idea. In fact, it's such a bad idea that there's a name for it: the Constant Interface Antipattern (see Effective Java Item 17). The problem is that a class's use of the static members of another class is a mere implementation detail. When a class implements an interface, it becomes part of the class's public API. Implementation details should not leak into public APIs.
          The static import construct allows unqualified access to static members without inheriting from the type containing the static members. Instead, the program imports the members, either individually:
import static java.lang.Math.PI;
or en masse:
import static java.lang.Math.*;
Once the static members have been imported, they may be used without qualification:
double r = cos(PI * theta);

Metadata (Annotations)
Annotations provide data about a program that is not part of the program itself. They have no direct effect on the operation of the code they annotate.
Annotations have a number of uses, among them:
  • Information for the compiler — Annotations can be used by the compiler to detect errors or suppress warnings.
  • Compiler-time and deployment-time processing — Software tools can process annotation information to generate code, XML files, and so forth.
  • Runtime processing — Some annotations are available to be examined at runtime.
Annotations can be applied to a program's declarations of classes, fields, methods, and other program elements.
The annotation appears first, often (by convention) on its own line, and may include elements with named or unnamed values:
@Author(
   name = "Benjamin Franklin",
   date = "3/27/2003"
)
class MyClass() { }
or
@SuppressWarnings(value = "unchecked")
void myMethod() { }
There are three annotation types that are predefined by the language specification itself: @Deprecated@Override, and @SuppressWarnings[example - @SuppressWarnings("deprecation")].

Annotation Processing
The more advanced uses of annotations include writing an annotation processor that can read a Java program and take actions based on its annotations. It might, for example, generate auxiliary source code, relieving the programmer of having to create boilerplate code that always follows predictable patterns. To facilitate this task, release 5.0 of the JDK includes an annotation processing tool, called apt. In release 6 of the JDK, the functionality of apt is a standard part of the Java compiler.
To make annotation information available at runtime, the annotation type itself must be annotated with @Retention(RetentionPolicy.RUNTIME), as follows:
import java.lang.annotation.*; 
@Retention(RetentionPolicy.RUNTIME)
@interface AnnotationForRuntime {
   // Elements that give information
   // for runtime processing
}

Virtual Machine
Class Data Sharing
  The class data sharing feature is aimed at reducing application startup time and footprint. The installation process loads a set of classes from the system jar file into a private, internal representation, then dumps that representation to a "shared archive" file. During subsequent JVM invocations, the shared archive is memory-mapped in, saving the cost of loading those classes and allowing much of the JVM's metadata for these classes to be shared among multiple JVM processes. For more information, click the above link.
   Class data sharing (CDS) is a new feature in J2SE 5.0 intended to reduce the startup time for Java programming language applications, in particular smaller applications, as well as reduce footprint. When the JRE is installed on 32-bit platforms using the Sun provided installer, the installer loads a set of classes from the system jar file into a private internal representation, and dumps that representation to a file, called a "shared archive". Class data sharing is not supported in Microsoft Windows 95/98/ME. If the Sun JRE installer is not being used, this can be done manually, as explained below. During subsequent JVM invocations, the shared archive is memory-mapped in, saving the cost of loading those classes and allowing much of the JVM's metadata for these classes to be shared among multiple JVM processes.
   In J2SE 5.0, class data sharing is supported only with the Java HotSpot Client VM, and only with the  serial garbage collector.
The primary motivation for including CDS in the 5.0 release is the decrease in startup time it provides. CDS produces better results for smaller applications because it eliminates a fixed cost: that of loading certain core classes. The smaller the application relative to the number of core classes it uses, the larger the saved fraction of startup time.
 The footprint cost of new JVM instances has been reduced in two ways. First, a portion of the shared archive, currently between five and six megabytes, is mapped read-only and therefore shared among multiple JVM processes. Previously this data was replicated in each JVM instance. Second, since the shared archive contains class data in the form in which the Java Hotspot VM uses it, the memory which would otherwise be required to access the original class information in rt.jar is not needed. These savings allow more applications to be run concurrently on the same machine. On Microsoft Windows, the footprint of a process, as measured by various tools, may appear to increase, because a larger number of pages are being mapped in to the process' address space. This is offset by the reduction in the amount of memory (inside Microsoft Windows) which is needed to hold portions on rt.jar. Reducing footprint remains a high priority.


Garbage Collector Ergonomics
The parallel collector has been enhanced to monitor and adapt to the memory needs of the application. You can specify performance goals for applications and the JVM will tune the size of the Java heap to meet those performance goals with the smallest application footprint consistent with those goals. The goal of this adaptive policy is to eliminate the need to tune command-line options to achieve the best performance. For a synopsis of garbage collection features, click the above link.

The following changes take effect with J2SE 5.0.
on server-class machines running the server VM, the garbage collector (GC) has changed from the previous serial collector (-XX:+UseSerialGC) to a parallel collector (-XX:+UseParallelGC). You can override this default by using the -XX:+UseSerialGC command-line option to the java command.
  1. On server-class machines running either VM (client or server) with the parallel garbage collector (-XX:+UseParallelGC) the initial heap size and maximum heap size have changed as follows.
initial heap size:
Larger of 1/64th of the machine's physical memory on the machine or some reasonable minimum. Before J2SE 5.0, the default initial heap size was a reasonable minimum, which varies by platform. You can override this default using the -Xms command-line option.
maximum heap size:
Smaller of 1/4th of the physical memory or 1GB. Before J2SE 5.0, the default maximum heap size was 64MB. You can override this default using the -Xmx command-line option.

Server-Class Machine Detection
At application startup, the launcher can attempt to detect whether the application is running on a "server-class" machine.
Starting with J2SE 5.0, when an application starts up, the launcher can attempt to detect whether the application is running on a "server-class" machine and, if so, use the Java HotSpot Server Virtual Machine (server VM) instead of the Java HotSpot Client Virtual Machine (client VM). The aim is to improve performance even if no one configures the VM to reflect the application it's running. In general, the server VM starts up more slowly than the client VM, but over time runs more quickly.
Note: For J2SE 5.0, the definition of a server-class machine is one with at least 2 CPUs and at least 2GB of physical memory.
In J2SE 5.0, server-class detection occurs if neither -server nor -client is specified when launching the application on an i586 or Sparc 32-bit machine running Solaris or Linux. As the following table shows, the i586 Microsoft Windows platform is not subject to the server-class test (i.e., is never treated as a server-class machine by default) and uses the client VM by default. The remaining Sun-supported platforms use only the server VM.
J2SE Development Kit 5.0 has several enhancments in the java.lang.* and java.util.* packages, including:
·         ProcessBuilder - The new ProcessBuilder class provides a more convenient way to invoke subprocesses than does Runtime.exec. In particular, ProcessBuilder makes it easy to start a subprocess with a modified process environment (that is, one based on the parent's process environment, but with a few changes).
·         Formatter - An interpreter for printf-style format strings, the Formatter class provides support for layout justification and alignment, common formats for numeric, string, and date/time data, and locale-specific output. Common Java types such as bytejava.math.BigDecimal , andjava.util.Calendar are supported. Limited formatting customization for arbitrary user types is provided through the java.util.Formattable interface.
·         Scanner - The java.util.Scanner class can be used to convert text into primitives or Strings. Since it is based on the java.util.regex package, it also offers a way to conduct regular expression based searches on streams, file data, strings, or implementors of the Readable interface.
·         Concurrency Utilities The java.util.concurrentjava.util.concurrent.atomic, and java.util.concurrent.locks packages provide a extensible framework of high-performance, scalable, thread-safe building blocks for developing concurrent classes and applications, including thread pools, thread-safe collections, semaphores, a task scheduling framework, task synchronization utilities, atomic variables, and locks. Additionally, these packages provide low-level primitives for advanced concurrent programming which take advantage of concurrency support provided by the processor, enabling you to implement high-performance, highly scalable concurrent algorithms in Java to a degree not previously possible without using native code. For more information, refer to JSR 166 .
·         Collections Framework Enhancements - There are many enhancements to the Collections framework.
·         Instrumentation - The new java.lang.instrument package provides services that allow Java programming agents to instrument programs running on the Java virtual machine by modifying methods' bytecodes at runtime.
·         Threads - The java.lang.Thread class has the following enhancements:

o    Thread priority handling has changed.
o    Thread.State enum class and the new getState() API are provided for querying the execution state of a thread.
o    The new thread dump API - the getStackTrace and getAllStackTraces methods in the Thread class - provides a programmatic way to obtain the stack trace of a thread or all threads.
o    The uncaughtExceptionHandler mechanism, previously available only through the ThreadGroup class, is now available directly through the Thread class.
o    A new form of the sleep() method is provided which allows for sleep times smaller than one millisecond.

Scanner
The java.util.Scanner class can be used to convert text into primitives or Strings. Since it is based on the java.util.regex package, it also offers a way to conduct regular expression based searches on streams, file data, strings, or implementors of the Readable interface. A simple text scanner which can parse primitive types and strings using regular expressions.
Scanner breaks its input into tokens using a delimiter pattern, which by default matches whitespace. The resulting tokens may then be converted into values of different types using the various next methods.  For example, this code allows a user to read a number from System.in:
     Scanner sc = new Scanner(System.in);
     int i = sc.nextInt();

Concurrency Utilities
The java.util.concurrentjava.util.concurrent.atomicand java.util.concurrent.locks packages provide a powerful, extensible framework of high-performance, scalable, thread-safe building blocks for developing concurrent classes and applications, including thread pools, thread-safe collections, semaphores, a task scheduling framework, task synchronization utilities, atomic variables, and locks. The addition of these packages to the core class library frees the programmer from the need to craft these utilities by hand, in much the same manner that the Collections Framework did for data structures. Additionally, these packages provide low-level primitives for advanced concurrent programming which take advantage of concurrency support provided by the processor, enabling programmers to implement high-performance, highly scalable concurrent algorithms in the Java language to a degree not previously possible without resorting to native code. Refer to JSR 166 .

Threads
The java.lang.Thread class has the following enhancements:
      .Thread priority handling has changed; see the above link for details.
      ·  Thread.State enum class and the new getState() API are provided for querying the execution state of a thread.
   · The new thread dump API - the getStackTrace and getAllStackTraces methods in the Thread class - provides a programmatic way to obtain the stack trace of a thread or all threads.
      ·  The uncaughtExceptionHandler mechanism, previously available only through the ThreadGroup class, is now available directly through the Thread class.

·         A new form of the sleep() method is provided which allows for sleep times smaller than one millisecond.
The Concurrency Utilities includes:
  • Task Scheduling Framework - The Executor framework is a framework for standardizing invocation, scheduling, execution, and control of asynchronous tasks according to a set of execution policies. Implementations are provided that allow tasks to be executed within the submitting thread, in a single background thread (as with events in Swing), in a newly created thread, or in a thread pool, and developers can create of Executor supporting arbitrary execution policies. The built-in implementations offer configurable policies such as queue length limits and saturation      policy which can improve the stability of applications by preventing runaway resource consumption.
  • Concurrent Collections - Several new Collections classes have been added, including the new Queue and BlockingQueue interfaces, and high-performance, concurrent implementations of MapList, and Queue.
  • Atomic Variables - Classes for atomically manipulating single variables (primitive types or references), providing high-performance atomic arithmetic and compare-and-set methods. The atomic variable implementations in java.util.concurrent.atomicoffer higher performance than would be available by using synchronization (on most platforms), making them useful for implementing high-performance concurrent algorithms as well as conveniently implementing counters and sequence number generators.
  • Synchronizers - General purpose synchronization classes, including semaphores,mutexesbarrierslatches, and exchangers, which facilitate coordination between threads.
  • Locks - While locking is built into the Java language via the synchronized keyword, there are a number of inconvenient limitations to built-in monitor locks. The java.util.concurrent.locks package provides a high-performance lock implementation with the same memory semantics as synchronization, but which also supports specifying a timeout when attempting to acquire a lock, multiple condition variables per lock, non-lexically scoped locks, and support for interrupting threads which are waiting to acquire a lock.
  • Nanosecond-granularity timing - The System.nanoTime method enables access to a nanosecond-granularity time source for making relative time measurements, and methods which accept timeouts (such as the BlockingQueue.offerBlockingQueue.poll,Lock.tryLock,Condition.await, and Thread.sleep) can take timeout values in nanoseconds. The actual precision of System.nanoTime is platform-dependen

Tuesday, 21 July 2015

Java 7: The Top 8 Features

It’s been a while since the last major Java release and expectations were naturally high for the upcoming release. The Java 7 release initially included many JSRs with exciting features, like support for closures, which were later deferred to Java 8 in order to release JSRs that are already done. This effectively diluted what is now offered in Java 7 and has left some disappointed.

The Java language has undergone major changes since I started using it in 1998. Most of the changes were driven by the Java Community Process (JCP) which was established in 1998 as a formal and transparent process to let interested individuals and entities participate and influence how the language should evolve. This is done through the submission of a change request, known as Java Specification Request (JSR), followed by a review and a voting process. Changes or enhancements made to the language can be usually tracked back to a JSR where they were originally put forward for review. For example, the addition of Generics in Java 5 was done via JSR 14.

Java Releases

Here’s a quick snapshot of the past Java release dates (table 1). There are several small new features and enhancements in Java 7. Out of the 28 features that I looked at, here are the ones that I found useful.


New features and enhancements

#1 Strings in switch

In programming, we often encounter situations where we need to do different things based on different values of a variable. For Boolean variables, an if-then-else statement is the perfect way of branching code. For primitive variable types we use the switch statement. However, for String variables, we tend to resort to using multiple if-then-else branches as follows.

Java 6 and Before

One workaround for this is to convert the String into an enum and then switch on the enum.

Java 7

Java 7, however, has added a language level support for String in switch. Now you can rewrite the same code more elegantly:


Not only does this help us write more readable code, but it also helps the compiler generate more efficient byte code as compared to the if-then-else by actually switching on the hashcode() and then doing an equals() comparison. Please note that you will get a NullPointerException if the variable language in the above example resolves to null. I like this feature, but unlike some of the other enhancements in the past (like Generic in Java 5), I don’t anticipate using this feature a lot. Practically, I find myself using if-then-else for one or two values and resort to an Enum when the number of values are higher.

#2 try-with-resources statement

One of the most useful additions in Java 7 is the auto closing of resources like InputStream which helps us reduce boiler plate code from our programs. Suppose we were writing a program which reads a file and closes the FileInputStream when it’s done, here is how you would write the program:

With Java 6 and Before

I want to point out a couple of things in this code. Firstly, notice that we declare the FileInputStream outside the try block just so that it can be accessed in the finally block. The second observation is that we need to initialize the InputStream to null, so that it is guaranteed to be initialized when we access it in the finally block. Last but not the least, the is.close() in the finally block may throw an Exception as well, thereby hiding the original Exception thrown in the try block Exception from the caller. What we probably want is to handle the Exception thrown from is.close() and throw the original IOException.


The above code still has a shortcoming that the Exception thrown from finally is supressed and not accessible to the calling code. I’m not sure how often we want to get both the original Exception and also the Exception thrown from the finally block, but if we did want it, we could do always do something like this:


SuppressedException above is a user written Java bean with a field named suppressed of type Exception. The calling code can then call SupressedException.getThreadLocal().getException() to get the Exception that was supressed in the finally clause. Great, we solved all the problems associated with the try-catch-finally! Now we must remember to repeat this exact sequence with each use of try-catch-finally when handling files or other resources which need to be closed. Enter Java 7, and we can do the above without the boiler plate code.

With Java 7

 
try can now have multiple statements in the parenthesis and each statement should create an object which implements the new java.lang.AutoClosable interface. The AutoClosable interface consists of just one method.


Each AutoClosable resource created in the try statement will be automatically closed! If an exception is thrown in the try block and another Exception is thrown while closing the resource, the first Exception is the one eventually thrown to the caller. The second Exception is available to the caller via the ex.getSupressed() method. Throwable.getSupressed() is a new method added on Throwable in Java 7 just for this purpose.
               

Mandatory catch block when using the try statement

Note that if you are creating AutoClosable resources in the try block, you are required to declare a catch block to catch the concrete exception thrown from the actual AutoClosable. close() method. Alternatively you need to throw the Exception. Think of the close() method as implicitly being called as the last line in the try block. So, if an application has its own AutoClosable class as follows:


Then, the following will cause a compile error:


To fix the above, you need to catch or throw the Exception from the calling method.


Syntax for declaring multiple resources

The try statement can contain multiple statements separated by semicolon. Each statement must result in an AutoClosable object.


It is illegal to declare any variable which isn’t an AutoClosable.


Output

ERROR: try-with-resources not applicable to variable type
required: AutoCloseable
found: long

AutoClosable vs Closable

The old Closable interface introduced in Java 5, which also has the same method that now extends from AutoClosable, implying that all Closable classes are automatically Auto-Closable. Those classes automatically become resources that can be created in the try statement. The slight difference in AutoClosable and Closable is that unlike Closable.close(), AutoClosable.close() is not supposed to be idempotent, which means that calling it twice can have side effects. The second difference is that since exceptions thrown from AutoClosable. close() are suppressed, AutoClosable.close() should not throw exceptions which can cause problems when suppressed, like the InterruptedException.

#3 More precise rethrow

There are often situations when we want to catch multiple exceptions of different types, do “something” with them, and rethrow them. Let us consider this example, where we have some code which throws IOException and SQLException.



In the above example, we are logging each type of exception being thrown by the try block before rethrowing them. This results in a duplication of code in the catch blocks. Before Java 7, to get around the code duplication issue we would catch the base exception as follows:


However, this requires us to rethrow the base Exception type java.lang.Exception from the calling method.
public static void main(String[] args) throws Exception {

With Java 7

Java 7 has added the “precise rethrow” feature which lets you catch and throw the base exception while still throwing the precise exception from the calling method.

 
Note the keyword final in the above catch clause. When a parameter is declared final, the compiler statically knows to only throw those checked exceptions that were thrown by the try block and were not caught in any preceding catch blocks.

#4 Multi-catch

There is no elegant way with Java 6 to catch multiple exceptions of different types and handle them in the same way.

You can always catch the parent Exception in order to avoid duplication of code, but it is not always suitable especially if the parent is java.lang.Exception. Java 7 lets you catch multiple Exceptions in a single catch block by defining a “union” of Exceptions to be caught in the catch clause.


Note that the pipe ‘|’ character is used as the delimiter. The variable ‘ex’ in the above example is statically typed to the base class of Ex1 and Ex2, which is java.lang.Exception in this case.

#5 Binary integral literals

With Java 7, you can now create numerical literals using binary notation using the prefix “0b”

int n = 0b100000;
System.out.println(“n = ” + n);

Output

n = 32

#6 Underscores in numeric literals

With Java 7, you can include underscores in numeric literals to make them more readable. The underscore is only present in the representation of the literal in Java code, and will not show up when you print the value.

Without underscore

int tenMillion = 10000000;
System.out.println(“Amount is “ + tenMillion);

Output

10000000

With underscore

int tenMillionButMoreReadable = 10_000_000;
System.out.println(“Amount is ” + tenMillionButMoreReadable);

Output

10000000

More rules and examples

1. Consecutive underscores is legal.

int n = 1000______000;

2. Underscores can be included in other numeric types as well.

double d = 1000_000.0d;
long l = 1000_000l;
int hex = 0xdead_c0de;
int bytes = 0x1000_0000;

3. Underscore can be included after the decimal point.

double example8 = 1000_000.000_000d;

4. It is illegal to start a literal with an underscore


5. It is illegal to end a literal with an underscore.


6. It is also illegal to have underscore be just before or after a decimal point.


               
7. Improved type inference for generic instance creation

Java 5 introduced generics which enabled developers to write type safe collections. However, generics can sometimes be too verbose. Consider the following example where we are creating a Map of List of String.

With Java 5 and 6

Map<String, List<String>> retVal = new HashMap<String, List<String>>();

Note that the full type is specified twice and is therefore redundant. Unfortunately, this was a limitation of Java 5 and 6.

With Java 7

Java 7 tries to get rid of this redundancy by introducing a left to right type inference. You can now rewrite the same statement by using the <> construct.

Map<String, List<String>> retVal = new HashMap<>();

This does make the code a little less verbose. You can also use <> construct when returning a newly created object.


This, in my opinion, goes only half way. The full solution would have been a right to left full type inference.

Map map = new HashMap<String, String>();

The above would have made the code even less verbose. Though this enhancement can still be done in a later version.

#8 More new I/O APIs for the Java platform (NIO.2)

A new set of I/O APIs and features were introduced in Java 1.4 under the java.nio package. This addition was called the New I/O APIs, also known as NIO. Naming something New is always short-sighted because it will not remain new forever. When the next version comes along, what should the new version be called, the NEW NEW I/O? Java 1.7 offers a rich set of new features and I/O capabilities, called NIO.2 (New I/O version 2?). Here are the key highlights of NIO.2.

a) Package

The most important package to look for is java.nio.file. This package contains many practical file utilities, new file I/O related classes and interfaces.

b) The java.nio.file.Path interface

Path is probably the new class that developers will use most often. The file referred by the path does not need to exist. The file referred to does not need to exist. For all practical purposes, you can think of replacing java.io.File with java. io.Path.

Old Way

File file = new File(“hello.txt”);
System.out.println(“File exists() == ” + file.exists());

New Way

Path path = FileSystems.getDefault().getPath(“hello.txt”);
System.out.println(“Path exists() == ” + Files.exists(path));

c) The java.nio.file.Files class

The Files class offers over 50 utility methods for File related operations which many developers would have wanted to be a part of earlier Java releases. Here are some methods to give you a sense of the range of methods offered. • copy() – copy a file, with options like REPLACE_EXISTING, NOFOLLOW_LINKS public static Path copy(Path source, Path target, CopyOption… options);

• move() – move or rename a file public static Path move(Path source, Path target, CopyOption… options);

• newInputStream() – create input stream public static InputStream newInputStream(Path path, OpenOption… options);

• readAllBytes() – similar to the Apache IOUtils.readFile-ToByteArray public static byte[] readAllBytes(Path path) throws IOException;

• createSymbolicLink() – creates a symbolic link, if supported by the file system public static Path createSymbolicLink(Path link, Path target, FileAttribute<?>… attrs) throws IOException


d) WatchService API

WatchService API is a new feature introduced in Java 1.7. It provides an API that lets you “listen” to a certain type of file system events. Your code gets called automatically when those events occur. Examples of event types are captured by StandardWatchEventKinds class.

• ENTRY_CREATE:an entry is created or renamed in the directory
• ENTRY_DELETE:an entry is created or renamed out of the directory
• ENTRY_MODIFY:a directory entry is modified

Example
Here’s a full example of how to watch a directory and print any newly created files.


Run the above program. Then create a file ‘new.txt’ in the directory ‘logs’. The program will print:
logs: new file created new.txt

Note about WatchService implementation

The implementation will take advantage of native support for file change notification when supported by the native file system, but will resort to polling otherwise.

IDE Support

Java 7 support is now available in NetBeans and IntelliJ. Eclipse does not support Java 7 yet. The upcoming release of Eclipse 3.7 will not have support for Java 7 either, but support will be added in 3.7 SR1, expected September 2011 (table 2).

Conclusion

Java 7 offers many small language enhancements and features. However, I did not find any feature as compelling as Regex enhancement in Java 1.4 or Generics, Auto-boxing or Enum enhancement in Java 1.5. I find the try-with-resources enhancement particularly useful and am looking forward to using it. I also look forward to using new features from the NIO.2 library. Overall, I am glad that something was released this year as opposed to releasing a monolith of changes next year.