Example:
try {A enhanced version might look like this.
FileReader fr = new FileReader("Readme.txt");
fr.read();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
try(new LogAndContinueExceptionHandler()){LogAndContinueExceptionHandler looks like this.
FileReader fr = new FileReader("Readme.txt");
fr.read();
}
private static interface ExceptionHandler {If all you are going to do is log the exception, then maybe a default implementation in Logger makes sense.
public void uncaughtException(Runnable source, Throwable e);
}
public class LogAndContinueExceptionHandler implements ExceptionHandler{
@Override
public void uncaughtException(Runnable source, final Throwable e) {
Logger.getLogger("ErrorLogger").log(Level.SEVERE, e.getMessage(), e);
}
}
try(Logger.logALL("MyLogName")){And for all of you who think checked exception are the bane of all existence there is this option.
FileReader fr = new FileReader("Readme.txt");
fr.read();
}
public class ToRuntime implements ExceptionHandler{This rethrows any exception it gets a hold of as a runtime exception. This would drive me nuts, but some people really do hate checked exceptions.
@Override
public void uncaughtException(Runnable source, final Throwable e) {
throw new RuntimeException(e);
}
}
It would be nice to be able to supply different logic for different types of exceptions, just like you do in a try/catch block. Also if one could handle some logic in the reusable section and override that by implementing a catch block you could get more flexibility.
Example:
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException e1) {
e1.printStackTrace();
} catch (InstantiationException e1) {
e1.printStackTrace();
} catch (IllegalAccessException e1) {
e1.printStackTrace();
} catch (UnsupportedLookAndFeelException e1) {
e1.printStackTrace();
}
try(new ReflectionHandeler()){
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (UnsupportedLookAndFeelException e1) {
e1.printStackTrace();
}
public class ReflectionHandeler implements ExceptionHandler{
public void uncaughtException(Runnable source, final ClassNotFoundException e) {
// do something important
}
public void uncaughtException(Runnable source, final InstantiationException e) {
// do something important
}
public void uncaughtException(Runnable source, final IllegalAccessException e) {
// do something important
}
}
ReflectionHandeler might be useful someplace else... Ok this wasn't the best example, but you get the idea. Some get caught in the handler and some get caught in the catch.
Where a pattern for handling an exception or types of exceptions is repeatable building a reusable part can help unclutter and your code and make it more maintainable. Now if the task of handling a particular type of exception changes code need only be changed in one place, not scattered throughout the code in try blocks.
It's an idea. I may try to hack the javac compiler to support something like this... not that I'm sure even where to begin.
5 comments:
Nice idea! May I recommend trying it in Kijaro, the no-nonsense sandbox set up by Stephen Colebourne?
It's similiar to the control invocation syntax of the BGGA proposal, right? http://www.javac.info/closures-v05.html
@Casper
Thanks, Yes I really should try to implement this. I'll have to see if Kijaro will except me.
@David
It does turns out to look like the the control invocation syntax. It's not really a closure. It's just a delegate object for the exception handling logic.
Cool Idea,
really useful if only want to be doing logging or some common tasks on the exceptions.
But I think it will become more verbose when you need to have different exception handling codes in different scenarios.
The problem with a non-local exception handler is that you have no access to local variables. Maybe you could pass some of them to the handler?
Post a Comment