Java 7: Try-with-Resources Statement
Before Java 7, handling resources such as files, streams, and database connections required meticulous boilerplate code. Developers had to explicitly close these resources in a finally block to prevent memory leaks and ensure system stability. This approach was error-prone; if an exception occurred in the try block and another exception was thrown while closing the resource in the finally block, the original exception was often masked or lost, making debugging incredibly difficult.
Java 7 introduced the Try-with-Resources statement, a monumental improvement for resource management. It guarantees that any resource opened within the try(...) clause will be closed automatically at the end of the statement, regardless of whether the try block completes normally or an exception is thrown. This elegant solution drastically reduces boilerplate code and eliminates the need for explicit finally blocks just for resource cleanup.
To use Try-with-Resources, the resource being managed must implement the java.lang.AutoCloseable interface, or its sub-interface java.io.Closeable. Almost all standard Java I/O and JDBC classes were updated in Java 7 to implement these interfaces. Furthermore, if multiple resources are opened in a single try statement, they are closed in the reverse order of their creation, ensuring safe and predictable teardown.
Another significant advantage is how it handles suppressed exceptions. If an exception is thrown both in the try block and during the automatic close() invocation, the exception from the try block is propagated, and the exception from close() is added to it as a "suppressed" exception, which can be retrieved later. This preserves the most critical error information for developers.
How it Works
You declare one or more resources inside the parentheses immediately following the try keyword. The scope of these resource variables is limited to the try block. When the block finishes execution, the JVM automatically calls the close() method on each resource. You can still use catch and finally blocks alongside Try-with-Resources, and they will execute after the resources have been closed.
Java Example
Scenario 1: Reading a file using BufferedReader
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
public class TryWithResourcesExample1 {
public static void main(String[] args) {
// Assume "test.txt" contains the text "Hello, Java 7!"
try (BufferedReader br = new BufferedReader(new FileReader("test.txt"))) {
String line;
while ((line = br.readLine()) != null) {
System.out.println("Read from file: " + line);
}
} catch (IOException e) {
System.out.println("Exception caught: " + e.getMessage());
}
}
}
Output
Read from file: Hello, Java 7!
Scenario 2: Managing Multiple Resources
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
public class TryWithResourcesExample2 {
public static void main(String[] args) {
try (InputStream is = new FileInputStream("input.txt");
OutputStream os = new FileOutputStream("output.txt")) {
System.out.println("Both input and output streams opened successfully.");
int data = is.read();
if (data != -1) {
os.write(data);
}
System.out.println("Data copied successfully.");
} catch (IOException e) {
System.out.println("I/O Error: " + e.getMessage());
}
}
}
Output
Both input and output streams opened successfully.
Data copied successfully.
Scenario 3: Custom AutoCloseable Resource
class MyResource implements AutoCloseable {
public void doSomething() {
System.out.println("Resource is doing something...");
}
@Override
public void close() throws Exception {
System.out.println("Custom Resource closed automatically.");
}
}
public class TryWithResourcesExample3 {
public static void main(String[] args) {
try (MyResource resource = new MyResource()) {
resource.doSomething();
} catch (Exception e) {
e.printStackTrace();
}
}
}
Output
Resource is doing something...
Custom Resource closed automatically.
Key Points
- Resources must implement
AutoCloseableorCloseable. - Resources are closed in the reverse order of their declaration.
- Eliminates boilerplate
finallyblocks for resource closure. - Handles suppressed exceptions gracefully, preventing primary exceptions from being swallowed by closure errors.
Comments