Why close method of java.lang.AutoCloseable throws Exception, but close method of java.io.Closeable throws IOException?
Solution 1
The AutoClosable
interface is located in java.lang
and is intended to be applied to any resource that needs to be closed 'automatically' (try-with-resources). The AutoClosable
must not be an io releated resource. So the interface can not make any assumption of a concrete exception.
On the other hand Closable
is located in java.io
and extends AutoClosable
, because a Closable
is an AutoClosable
for io resources. Therefore it declares that IOException
s can be thrown on close.
For example... a java.sql.Connection
is an AutoClosable
because it's close method throws SQLException
and a SQLException
is not an IOException
. Think about in memory DBs and it makes sense that closing an sql connection must not throw an IOException
.
EDIT
answered one more doubt i.e. why AutoClosable is kept under java.lang package. Thanks.
I think it is located in java.lang
because try-with-resources was introduced as a language feature in Java 1.7. Thus java.lang
Solution 2
Further to being able to throw some other types of exceptions than IOException
one beautiful and common use case can be easily overseen:
One can override the interface to have no throws
declaration at all, thus permitting try
being written without explicit exception handling.
In our code we have an interface Searcher
declared in the following way
public interface Searcher<V> extends AutoCloseable {
Stream<V> search();
@Override
void close();
}
This permits the following use of Searcher
instances:
try (Searcher<Datatype> dataTypeSearcher = new DataTypeSearcher(query)) {
return dataTypeSearcher.search();
}
// without any catch statements
If no throws
declaration was present on AutoCloseable
, the above would be the only usage as it would not be possible to override the AutoCloseable
interface throwing an exception not declared on the parent. The way it is currently done, both options are possible.
Solution 3
Closeable
extends AutoCloseable
, but there could be other particular interfaces that extend this interface. E.g.:
public interface MyCloseable extends AutoCloseable {
void close() throws RuntimeException;
}
They wanted to have an interface that can be used in many cases, and this is why they decided to use Exception
because it also works for other types of exceptions.
Vishrant
My first computer was a Dell Pentium III with 128 MB of RAM and 20 GB of HDD and HTML was my first computer language (markup) followed by Visual Basic 6.0 programming language. I am a polyglot programmer. I code because it's fun. I believe my today's code must be better than what I wrote yesterday. I love to explore new things.
Updated on June 17, 2022Comments
-
Vishrant almost 2 years
I was reading this link for
try-with-resources
and it says:The close method of the
Closeable
interface throws exceptions of typeIOException
while the close method of theAutoCloseable
interface throws exceptions of typeException
.But why? The close method of
AutoCloseable
could have also thrownIOException
is there any example that support that close method ofAutoCloseable
must throw exceptions of typeException
-
Vishrant over 9 yearsanswered one more doubt i.e. why
AutoClosable
is kept underjava.lang
package. Thanks. -
René Link over 9 years@Vishrant I updated my answer... Late but I hope not too late :)
-
entonio almost 7 yearsIn fact, answered why
AutoCloseable
was created at all instead of just reusingCloseable
. -
Paulo over 5 yearsVery good answer, René. Another way to put it is this: remember that
Closeable
existed before Java 1.7 and it'sclose
method was already throwingIOException
; I imagine that, when they introducedAutoCloseable
and retrofitedCloseable
to extend it, they found that theAutoCloseable.close
would necessarily have to throw a checked exception (inheritance/method overriding rules);Exception
was the most sensible option in this case. -
Alan over 4 years
The AutoClosable must not be an io releated resource.
This is incorrect and may be made correct by changing "must" to "may".