Tässä opetusohjelmassa opit kokeilemaan resursseja -säännön sulkea resurssit automaattisesti.
try-with-resources
Toteamus sulkee automaattisesti kaikki resurssit lopussa julkilausuman. Resurssi on objekti, joka suljetaan ohjelman lopussa.
Sen syntaksi on:
try (resource declaration) ( // use of the resource ) catch (ExceptionType e1) ( // catch block )
Kuten yllä olevasta syntaksista nähdään, julistamme try-with-resources
lausunnon
- ilmoitetaan ja välitetään resurssi
try
lausekkeessa. - määrittelemällä ja käsittelemällä kaikki poikkeukset, joita saattaa aiheutua resurssin sulkemisen yhteydessä.
Huomautus: Try-with-resources-käsky sulkee kaikki resurssit, jotka toteuttavat AutoCloseable-käyttöliittymän.
Otetaan esimerkki, joka toteuttaa try-with-resources
lausunnon.
Esimerkki 1: kokeile resursseja
import java.io.*; class Main ( public static void main(String() args) ( String line; try(BufferedReader br = new BufferedReader(new FileReader("test.txt"))) ( while ((line = br.readLine()) != null) ( System.out.println("Line =>"+line); ) ) catch (IOException e) ( System.out.println("IOException in try block =>" + e.getMessage()); ) ) )
Tulosta, jos test.txt-tiedostoa ei löydy.
IOException try-with-resources-lohkossa => test.txt (Ei tällaista tiedostoa tai hakemistoa)
Tulosta, jos test.txt-tiedosto löytyy.
Syötä kokeile resursseja -lohko Line => testirivi
Tässä esimerkissä käytämme BufferedReader-esiintymää tietojen lukemiseen test.txt
tiedostosta.
BufferedReaderin julistaminen ja ilmentäminen try-with-resources
lausekkeen sisällä varmistaa, että sen esiintymä on suljettu riippumatta siitä, try
täydennetäänkö lause normaalisti vai onko se poikkeus.
Jos tapahtuu poikkeus, se voidaan käsitellä poikkeusten käsittelylohkoilla tai heittojen avainsanalla.
Tukahdutetut poikkeukset
Edellä olevassa esimerkissä try-with-resources
lausekkeesta voidaan heittää poikkeuksia, kun:
- Tiedostoa
test.txt
ei löydy. BufferedReader
Objektin sulkeminen .
try
Lohkosta voidaan myös heittää poikkeus, koska tiedoston lukeminen voi epäonnistua monista syistä milloin tahansa.
Jos poikkeuksia heitetään sekä try
lohkosta että try-with-resources
käskystä, lohkosta tehty poikkeus try
heitetään ja try-with-resources
lausekkeesta tehty poikkeus estetään.
Pakattujen poikkeusten haku
Java 7: ssä ja sitä uudemmissa versioissa estetyt poikkeukset voidaan hakea kutsumalla Throwable.getSuppressed()
menetelmä try
lohkon heittämästä poikkeuksesta .
Tämä menetelmä palauttaa taulukon kaikista estetyistä poikkeuksista. Saamme estetyt poikkeukset catch
lohkoon.
catch(IOException e) ( System.out.println("Thrown exception=>" + e.getMessage()); Throwable() suppressedExceptions = e.getSuppressed(); for (int i=0; i" + suppressedExceptions(i)); ) )
Kokeile-resurssien käytön edut
Tässä ovat try-with-resurssien käytön edut:
1. lopuksi esto, jota ei tarvita resurssin sulkemiseen
Ennen kuin Java 7 esitteli tämän ominaisuuden, jouduimme käyttämään finally
lohkoa varmistaaksemme, että resurssi on suljettu resurssivuotojen välttämiseksi.
Tässä on ohjelma, joka on samanlainen kuin esimerkki 1 . Tässä ohjelmassa olemme kuitenkin käyttäneet viimeistä estoa resurssien sulkemiseen.
Esimerkki 2: Sulje resurssi viimeisellä lohkolla
import java.io.*; class Main ( public static void main(String() args) ( BufferedReader br = null; String line; try ( System.out.println("Entering try block"); br = new BufferedReader(new FileReader("test.txt")); while ((line = br.readLine()) != null) ( System.out.println("Line =>"+line); ) ) catch (IOException e) ( System.out.println("IOException in try block =>" + e.getMessage()); ) finally ( System.out.println("Entering finally block"); try ( if (br != null) ( br.close(); ) ) catch (IOException e) ( System.out.println("IOException in finally block =>"+e.getMessage()); ) ) ) )
Tuotos
Syötä kokeilulohko Line => rivi test.txt-tiedostosta Syötä lopuksi lohko
Kuten voimme nähdä yllä olevasta esimerkistä, finally
lohkon käyttö resurssien puhdistamiseen tekee koodista monimutkaisemman.
Huomaa myös try… catch
lohko finally
lohkossa? Tämä johtuu siitä, että IOException
voi esiintyä myös sulkemalla BufferedReader
instanssin tämän finally
lohkon sisällä, joten se myös kiinni ja käsitellään.
try-with-resources
Lause tekee automaattisen resurssienhallinta . Meidän ei tarvitse sulkea resursseja nimenomaisesti, kun JVM sulkee ne automaattisesti. Tämä tekee koodista luettavamman ja helpommin kirjoitettavan.
2. kokeile resursseja, joissa on useita resursseja
Voimme ilmoittaa useamman kuin yhden resurssin try-with-resources
lausekkeessa erottamalla ne puolipisteellä;
Esimerkki 3: kokeile useita resursseja
import java.io.*; import java.util.*; class Main ( public static void main(String() args) throws IOException( try (Scanner scanner = new Scanner(new File("testRead.txt")); PrintWriter writer = new PrintWriter(new File("testWrite.txt"))) ( while (scanner.hasNext()) ( writer.print(scanner.nextLine()); ) ) ) )
Jos tämä ohjelma suoritetaan luomatta mitään poikkeuksia, Scanner
objekti lukee rivin testRead.txt
tiedostosta ja kirjoittaa sen uuteen testWrite.txt
tiedostoon.
Kun tehdään useita ilmoituksia, try-with-resources
lause sulkee nämä resurssit päinvastaisessa järjestyksessä. Tässä esimerkissä PrintWriter
objekti suljetaan ensin ja sitten Scanner
objekti suljetaan.
Java 9 -kokeile resurssien parannusta
Java 7: ssä try-with-resources
lause on rajoitettu . Resurssi on ilmoitettava paikallisesti sen lohkon sisällä.
try (Scanner scanner = new Scanner(new File("testRead.txt"))) ( // code )
Jos ilmoittaisimme resurssin Java 7: n lohkon ulkopuolelle, se olisi tuottanut virheilmoituksen.
Scanner scanner = new Scanner(new File("testRead.txt")); try (scanner) ( // code )
Tämän virheen korjaamiseksi Java 9 paransi try-with-resources
lausetta siten, että resurssin viitettä voidaan käyttää, vaikka sitä ei ilmoitettakaan paikallisesti. Yllä oleva koodi suoritetaan nyt ilman kääntövirheitä.