Я нахожусь в процессе обучения Java , и я не могу найти хорошее объяснение на implements Closeable
и в implements AutoCloseable
интерфейсах.
Когда я реализовал interface Closeable
, моя Eclipse IDE создала метод public void close() throws IOException
.
Я могу закрыть поток, используя pw.close();
без интерфейса. Но я не могу понять, как я могу реализовать close()
метод с помощью интерфейса. И какова цель этого интерфейса?
Также я хотел бы знать: как я могу проверить, IOstream
действительно ли было закрыто?
Я использовал базовый код ниже
import java.io.*;
public class IOtest implements AutoCloseable {
public static void main(String[] args) throws IOException {
File file = new File("C:\\test.txt");
PrintWriter pw = new PrintWriter(file);
System.out.println("file has been created");
pw.println("file has been created");
}
@Override
public void close() throws IOException {
}
Ответы:
Мне кажется, вы не очень хорошо разбираетесь в интерфейсах. В опубликованном вами коде нет необходимости реализовывать
AutoCloseable
.Вам нужно только (или нужно) реализовать
Closeable
или,AutoCloseable
если вы собираетесь реализовать свой собственныйPrintWriter
, который обрабатывает файлы или любые другие ресурсы, которые необходимо закрыть.В вашей реализации достаточно позвонить
pw.close()
. Вы должны сделать это в блоке finally:Приведенный выше код связан с Java 6. В Java 7 это можно сделать более элегантно (см. Этот ответ ).
источник
PrintWriter
? В частности,AutoClosable
объекты можно использовать во многих других случаях, чем простоPrintWriter
s ...PrintWriter
поэтому я упомянул его, чтобы быть более конкретным.AutoCloseable
? Лучше покажиtry-with-resources
вместо этого…AutoCloseable
(введено в Java 7) позволяет использовать идиому try-with-resources :Теперь вы можете сказать:
и JVM вызовет
close()
вас автоматически.Closeable
это более старый интерфейс.По какой-то причинеЧтобы сохранить обратную совместимость, разработчики языка решили создать отдельный. Это позволяет не только использовать всеCloseable
классы (например, бросание потоковIOException
) в try-with-resources, но также позволяет генерировать более общие проверенные исключения изclose()
.В случае сомнений пользуйтесь
AutoCloseable
, пользователи вашего класса будут благодарны.источник
Closeable.close()
бросаетIOException
. Многиеclose()
методы, которые могут выиграть от try-with-resources, генерируют другие проверенные исключения (например,java.sql.Connection.close()
такAutoCloseable.close()
бросаютException
. Изменение существующегоCloseable
контракта нарушит все существующие приложения / библиотеки, полагающиеся на контракт, которыйclose()
только генерирует,IOException
а не все (проверенные) исключения.Closeable.close()
требуется быть идемпотентным.AutoCloseable.close()
нет, хотя все же настоятельно рекомендуется.public void close( ) throws Exception
- используйте более конкретное исключение, если можете (например, IOException)Closeable
не гарантирует идемпотентность. Это требует идемпотентности в реализацииclose()
метода пользователем. А то,IOException
будет ли он более конкретным / подходящим, зависит от варианта использования.Closeable
extendsAutoCloseable
и специально предназначен для потоков ввода-вывода: он генерирует IOException вместо Exception и является идемпотентным, тогда как AutoCloseable не предоставляет этой гарантии.Все это объясняется в документации к обоим интерфейсам.
Реализация AutoCloseable (или Closeable) позволяет использовать класс в качестве ресурса конструкции try-with-resources, представленной в Java 7, что позволяет автоматически закрывать такие ресурсы в конце блока, без необходимости добавления блока finally, который закрывает ресурс явно.
Ваш класс не представляет собой закрываемый ресурс, и нет абсолютно никакого смысла в реализации этого интерфейса: IOTest не может быть закрыт. Невозможно даже создать его экземпляр, поскольку у него нет метода экземпляра. Помните , что средства реализации интерфейса , что есть есть- отношения между классом и интерфейсом. У вас здесь нет таких отношений.
источник
Вот небольшой пример
Вот результат:
источник
this.close()
или что-то в коде? Потому что он вызывается автоматически (на всякийtry-with-resources
Заявление.try-with-resources statement
Являетсяtry
утверждение , что говорит один или несколько ресурсов. Aresource
- это объект, который необходимо закрыть после того, как программа завершит работу с ним.try-with-resources statement
Гарантирует , что каждый ресурс закрыт в конце заявления. Любой реализующий объектjava.lang.AutoCloseable
, который включает в себя все реализующие объектыjava.io.Closeable
, может использоваться как ресурс.В следующем примере считывается первая строка из файла. Он использует экземпляр
BufferedReader
для чтения данных из файла.BufferedReader
- это ресурс, который необходимо закрыть после того, как программа завершит работу с ним:В этом примере ресурс, объявленный в инструкции try-with-resources, является BufferedReader. Оператор объявления появляется в круглых скобках сразу после ключевого слова try. Класс
BufferedReader
в Java SE 7 и новее реализует интерфейсjava.lang.AutoCloseable
. ПосколькуBufferedReader
экземпляр объявлен в операторе try-with-resource, он будет закрыт независимо от того, завершается ли оператор try нормально или внезапно (в результате того, что методBufferedReader.readLine
выбрасываетIOException
).До Java SE 7 можно было использовать
finally
блок, чтобы гарантировать, что ресурс закрыт, независимо от того, завершается ли оператор try нормально или внезапно. В следующем примереfinally
вместоtry-with-resources
оператора используется блок :Пожалуйста , обратитесь к документации .
источник
Недавно я прочитал книгу Java SE 8 Programmer Guide II.
Я нашел кое - что о разнице между
AutoCloseable
противCloseable
.AutoCloseable
Интерфейс был введен в Java 7. До этого, другой интерфейс существовал называетсяCloseable
. Это было похоже на то, что хотели разработчики языка, за следующими исключениями:Closeable
ограничивает тип создаваемого исключенияIOException
.Closeable
требует, чтобы реализации были идемпотентными.Разработчики языка делают упор на обратную совместимость. Поскольку изменять существующий интерфейс было нежелательно, они сделали новый под названием
AutoCloseable
. Этот новый интерфейс менее строг, чемCloseable
. ПосколькуCloseable
соответствует требованиямAutoCloseable
, он начал реализовываться,AutoCloseable
когда последний был представлен.источник
Closeable
», я бы предложил сказать: «Этот новый интерфейс можно использовать в более общих контекстах, где исключение, созданное во время закрытия, не обязательно является исключением IOException». Во вселенной Java быть «менее строгим» имеет негативный настрой.