Effective Exception Handling Practices in Java
Prefer catching specific exception types over broad ones like Exception. This clarifies the intent and facilitates targeted error recovery.
import java.io.FileInputStream;
import java.io.FileNotFoundException;
public class ExceptionSpecificityDemo {
public static void loadConfigFile(String path) {
try {
FileInputStream configFile = new FileInputStream(path);
// Process configuration
} catch (FileNotFoundException e) {
System.err.println("Configuration file not located: " + e.getMessage());
}
}
}
For resources implementing AutoCloseable, leverage the try-with-resources construct introduced in Java 7. This ensures automatic closure, preventing resuorce leaks.
import java.io.BufferedReader;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.io.IOException;
public class ResourceManagementDemo {
public static void displayFileContents(String fileName) {
try (BufferedReader reader = Files.newBufferedReader(Paths.get(fileName))) {
reader.lines().forEach(System.out::println);
} catch (IOException ex) {
System.err.println("Error reading file: " + ex.getMessage());
}
}
}
When designing methods, carefully decide whether to handle an exception locally or propagate it to the caller via the throws clause. This choice depends on the appropriate level for recovery.
public class ExceptionPropagationDemo {
public static int computeDivision(int numerator, int denominator) throws ArithmeticException {
if (denominator == 0) {
throw new ArithmeticException("Division by zero is undefined.");
}
return numerator / denominator;
}
public static void main(String[] args) {
try {
int result = computeDivision(10, 0);
} catch (ArithmeticException ae) {
System.err.println("Calculation failed: " + ae.getMessage());
}
}
}
Integrate a logging framework like SLF4J or Log4j instead of using printStackTrace() or System.err.println() for exception recording. This provides better control over output format, destination, and log levels.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class ExceptionLoggingDemo {
private static final Logger log = LoggerFactory.getLogger(ExceptionLoggingDemo.class);
public void executeTask() {
try {
// Code that may fail
} catch (IllegalStateException ise) {
log.error("Task execution aborted due to illegal state", ise);
}
}
}