Kluczowym zadaniem try-with-resources w Javie jest automatyczne i poprawne zwalnianie zasobów. Przed pojawieniem się tej konstrukcji w Javie 7, programiści musieli ręcznie zamykać zasoby w bloku finally. Prowadziło to do powielania kodu i częstych błędów.
W Javie 6 i wcześniejszych wersjach zasobami (otwarte pliki, strumienie, połączenia) trzeba było zarządzać ręcznie przez finally, co często prowadziło do wycieków.
Ręcznie napisany kod zamykania zasobów jest źródłem błędów, zwłaszcza przy pracy z wieloma wyjątkami i złożoną hierarchią bloków catch. Nie ma gwarancji wywołania close() w przypadku błędów.
Od Javy 7 pojawiła się składnia try-with-resources, która gwarantuje automatyczne wywołanie metody close() dla każdego zasobu implementującego interfejs AutoCloseable.
Przykład kodu:
try (BufferedReader reader = new BufferedReader(new FileReader("test.txt"))) { String line = reader.readLine(); System.out.println(line); } catch (IOException e) { e.printStackTrace(); } // reader automatycznie się zamyka
Kluczowe cechy:
AutoCloseable mogą być używane w try-with-resources.Pytanie 1: Jaki interfejs powinien implementować zasób używany w try-with-resources?
AutoCloseable. Każdy obiekt implementujący ten interfejs (lub Closeable) może być używany w tej konstrukcji.
Pytanie 2: W jakiej kolejności zamykane są zasoby, jeśli jest ich kilka w try-with-resources?
Zasoby są zamykane w odwrotnej kolejności do ich deklaracji (stos-LIFO):
try (A a = new A(); B b = new B()) { ... } // b.close() zostanie wywołane pierwsze, potem a.close()
Pytanie 3: Czy można używać try-with-resources dla niestandardowych obiektów, na przykład połączeń sieciowych, które nie mają implementacji AutoCloseable?
Nie, ale można ręcznie zaimplementować AutoCloseable w swojej klasie. Po tym obiekt stanie się kompatybilny z try-with-resources.
Programiści ręcznie zamykali połączenie JDBC i Statement przez finally. Przy wystąpieniu drugiego wyjątku zamknięcie Statement nie było wykonywane, połączenie „utknęło” i ukryło błąd.
Zalety:
Wady:
Po wprowadzeniu try-with-resources w module ładowania plików wszystkie strumienie są automatycznie zamykane, kod stał się znacznie krótszy, zniknęły błędy wycieku deskryptorów plików.
Zalety:
Wady: