Java try-with-resources (esimerkkien avulla)

Tässä opetusohjelmassa opit kokeilemaan resursseja -säännön sulkea resurssit automaattisesti.

try-with-resourcesToteamus 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-resourceslausunnon

  1. ilmoitetaan ja välitetään resurssi trylausekkeessa.
  2. 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-resourceslausunnon.

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.txttiedostosta.

BufferedReaderin julistaminen ja ilmentäminen try-with-resourceslausekkeen sisällä varmistaa, että sen esiintymä on suljettu riippumatta siitä, trytä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-resourceslausekkeesta voidaan heittää poikkeuksia, kun:

  • Tiedostoa test.txtei löydy.
  • BufferedReaderObjektin sulkeminen .

tryLohkosta voidaan myös heittää poikkeus, koska tiedoston lukeminen voi epäonnistua monista syistä milloin tahansa.

Jos poikkeuksia heitetään sekä trylohkosta että try-with-resourceskäskystä, lohkosta tehty poikkeus tryheitetään ja try-with-resourceslausekkeesta tehty poikkeus estetään.

Pakattujen poikkeusten haku

Java 7: ssä ja sitä uudemmissa versioissa estetyt poikkeukset voidaan hakea kutsumalla Throwable.getSuppressed()menetelmä trylohkon heittämästä poikkeuksesta .

Tämä menetelmä palauttaa taulukon kaikista estetyistä poikkeuksista. Saamme estetyt poikkeukset catchlohkoon.

 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 finallylohkoa 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ä, finallylohkon käyttö resurssien puhdistamiseen tekee koodista monimutkaisemman.

Huomaa myös try… catchlohko finallylohkossa? Tämä johtuu siitä, että IOExceptionvoi esiintyä myös sulkemalla BufferedReaderinstanssin tämän finallylohkon sisällä, joten se myös kiinni ja käsitellään.

try-with-resourcesLause 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-resourceslausekkeessa 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, Scannerobjekti lukee rivin testRead.txttiedostosta ja kirjoittaa sen uuteen testWrite.txttiedostoon.

Kun tehdään useita ilmoituksia, try-with-resourceslause sulkee nämä resurssit päinvastaisessa järjestyksessä. Tässä esimerkissä PrintWriterobjekti suljetaan ensin ja sitten Scannerobjekti suljetaan.

Java 9 -kokeile resurssien parannusta

Java 7: ssä try-with-resourceslause 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-resourceslausetta siten, että resurssin viitettä voidaan käyttää, vaikka sitä ei ilmoitettakaan paikallisesti. Yllä oleva koodi suoritetaan nyt ilman kääntövirheitä.

Mielenkiintoisia artikkeleita...