Which one to use is a matter of taste and convenience. Just make it as
easy on yourself to do it as possible, so you'll always do it!
That IOException in stream.close() is very important. Consider a
buffered stream. Until you do a close(), some of your output is still
in your buffer. If that output can't be written, you'll get an
IOException, so you're not fooled into thinking your output succeeded
and your data is safely in the file.
It's not just buffered streams, however, because buffering can happen
anywhere -- underlying libraries, operating system, network, driver,
etc. Until that close successfully completes, IO errors are are still
possible, and may indicate that your data was not successfully
written.
Generally, you want to handle IOException at a higher level than the
try/finally that does the close. Often, it should be in a different
method entirely -- one where you can do something about it -- retry,
report the problem to the user, etc.
In fact, if there's not a specific strategy at hand for dealing with
an exception, it should be handled at as high a level as possible.
Java's check/unchecked exceptions are a bit unfortunate, in that
regard. It's often better to wrap an exception in a RuntimeException
and rethrow, than to either try to handle it locally, or to change
your method signatures by adding a 'throws IOException' all over the
place.
Swallowing exceptions is probably NOT what you want your wrappers to
do. Not unless they're either very far out in your stack, or are also
implementing a specific recovery strategy. (Returning null or false is
generally not the best way to do that!)
I have, several times now, written a WrappedException class that
largely hides the fact that it's not the original exception, but is an
unchecked exception. Let's say you've got some code that throws
either SQLException or IOException. It may also throw
FileNotFoundException (which is an IOException), and this is declared
in your method. Rather than duplicate the two catch clauses, you can
write:
try {
.. code that is declared to throw SQLException and IOException ..
} catch (Exception ex) {
throw new
WrappedException(ex).rethrow(FileNotFoundException.class).rethrow();
}
If it's a FileNotFoundException, the first rethrow will rethrow the
original exception (ex).
If it's a RuntimeException or Error the second rethrow throws the
original exception (ex).
If it's an InvocationTargetException or NoClassDefError or a few
others where you never want the immediate exception, the second
rethrow thows the cause exception (ex.getCause()).
Unfortunately, I've always done this for employers, so I don't have a
full implementation to hand out. I should recreate it soon, however.
This approach gives you a consistent way of dealing with checked
exceptions you're not prepared to deal with in the current context.
Swallowing them, or even logging them, hides bugs.
Generally, you shouldn't print or log them at the deeper levels,
either. That should generally be done at the outermost level, where
they're really handled, so they only get logged once.
On Feb 8, 5:48 pm, Jason Proctor <[email protected]>
wrote:
> indeed -- i did investigate moving to this pattern, but i found that
> putting the assignment inside the try() allowed me to change my mind
> about having a catch() clause too with no other code changes inside
> the method.
>
> i have wrappers for common items that are closable, such as streams,
> readers/writers, cursors, etc, which check for null and swallow any
> exceptions, so it's only one line inside the finally().
>
> quite why stream.close() throws IOException is kinda beyond me though :-)
--
You received this message because you are subscribed to the Google
Groups "Android Developers" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to
[email protected]
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en