Programiranje

Java 101: Predstavitev osnovnih jezikov Java, 5. del

Prejšnja 1 2 Stran 2 Stran 2 od 2

Tipski sklep in generični konstruktorji za generične in negenerične razrede

Generični in ne-generični razredi lahko deklarirajo generične konstruktorje, v katerih ima konstruktor formalni seznam parametrov tipa. Na primer, lahko z generičnim konstruktorjem deklarirate naslednji generični razred:

 javni razred Box {public Box (T t) {// ...}} 

Ta izjava določa generični razred Škatla s formalnim parametrom tipa E. Določa tudi generični konstruktor s formalnim parametrom tipa T. Lahko ustvarite primer generičnega razreda in prikličete njegov konstruktor, kot sledi:

 novo polje ("Aggies") 

Ta izraz ustvari primerek Škatla, mimo Marmor do E. Tudi prevajalnik sklepa Vrvica kot Tdejanski argument tipa, ker je argument konstruktorja a Vrvica predmet.

Prevajalniki Pre-Java 7 sklepajo na dejanske argumente generičnega konstruktorja podobno kot pri generični metodi. Prevajalnik Java 7 pa lahko sklepa na dejanske argumente tipa generičnega razreda, ki se ustvari v kontekstu diamantnega operaterja. Upoštevajte naslednji primer:

 Box box = novo polje ("Aggies"); 

Pa tudi sklepati na tip Marmor za parameter formalnega tipa E generičnega razreda Škatla, tip prevajalnika oblikuje Vrvica za parameter formalnega tipa T konstruktorja tega generičnega razreda.

Majhna sprememba Project Coin # 8: Poenostavljeni klic metode varargs

Pred Java 7 je vsak poskus sklicevanja na varargs (spremenljivke, znane tudi kot spremenljiva arity) metoda z neobnovljivim tipom varargs je povzročila, da je prevajalnik prikazal opozorilo "nevarna operacija". Da bi odpravil možnost številnih podobnih opozorilnih sporočil (po eno na klicno mesto), je Java 7 opozorilo premaknila s klicnega mesta na deklaracijo metode.

Vrste, ki jih je mogoče ponovno namestiti in jih ni mogoče ponovno namestiti

A vrsta, ki jo je mogoče ponovno namestiti izpostavi svoje popolne informacije o tipu med izvajanjem. Primeri vključujejo primitivne tipe, negenerične tipe, surove tipe in klice nevezanih nadomestnih znakov. Nasprotno pa a vrsta, ki je ni mogoče ponovno namestiti ima informacije o tipu odstranjene v času prevajanja z izbrisom tipa, da se zagotovi binarna združljivost s knjižnicami Java in aplikacijami, ki so bile ustvarjene pred generiki. Primeri vključujejo Nastavite in Nastavite. Ker vrsta, ki jo ni mogoče popraviti, med izvajanjem ni na voljo v celoti, JVM ne more ugotoviti razlike med njimi Nastavite in Nastavite; med izvajanjem samo surov tip Nastavite Na voljo.

Lahko povzročijo splošne metode, ki vključujejo vhodne parametre vararg onesnaževanje kupa, pri katerem se spremenljivka parametriziranega tipa nanaša na objekt, ki ni tega parametriziranega tipa (na primer, če je bil surovi tip pomešan s parametriziranim tipom). Prevajalnik poroča o "nepreverjenem opozorilu", ker ni mogoče preveriti pravilnosti operacije, ki vključuje parametriziran tip (na primer klic oddaje ali metode).

Seznam 13 prikazuje onesnaženje kupa v kontekstu, ki ni varargov.

Seznam 13. Dokazovanje onesnaženja kupa v nevarargovem kontekstu

 uvoz java.util.Iterator; import java.util.Set; uvoz java.util.TreeSet; javni razred HeapPollutionDemo {public static void main (String [] args) {Set s = new TreeSet (); Nastavi ss = s; // nepreverjeno opozorilo s.add (novo celo število (42)); // drugo nepreverjeno opozorilo Iterator iter = ss.iterator (); while (iter.hasNext ()) {String str = iter.next (); // ClassCastException vržen System.out.println (str); }}} 

Spremenljiv ss ima parametriziran tip Nastavite. Ko java.util.Set na to se sklicuje s je dodeljena ss, prevajalnik ustvari nepreverjeno opozorilo. To počne, ker prevajalnik tega ne more določiti s se nanaša na a Nastavite tipa (ne). Rezultat je onesnaženje s kupom. (Prevajalnik omogoča tej dodelitvi, da ohrani združljivost s starejšimi različicami Jave, ki ne podpirajo generikov. Nastavite v Nastavite, kar ima za posledico eno Nastavite dodeljena drugemu Nastavite.)

Prevajalnik ustvari drugo nepreverjeno opozorilo v vrstici, ki prikliče Nastaviteje dodaj () metoda. To počne, ker ne more določiti, ali je spremenljivka s se nanaša na a Nastavite ali Nastavite tip. To je še ena situacija onesnaženja kupa. (Prevajalnik dovoli klic te metode, ker se izbris spremeni Nastaviteje logični dodatek (E e) metoda za logično dodajanje (objekt o), ki lahko naboru doda kakršen koli predmet, vključno z java.lang.Integer podvrsta java.lang.Object.)

Do onesnaženja kupa lahko zlahka pride v kontekstu varargov. Na primer, razmislite o seznamu 14.

Seznam 14. Dokazovanje onesnaženja kupa v kontekstu varargov

 uvoz java.util.Arrays; uvoz java.util.List; javni razred UnsafeVarargsDemo {public static void main (String [] args) {unsafe (Arrays.asList ("A", "B", "C"), Arrays.asList ("D", "E", "F") ); } statična void nevarna (Seznam ... l) {Objekt [] oArray = l; oArray [0] = Arrays.asList (novo Double (3.5)); Niz s = l [0] .get (0); }} 

The Objekt [] oArray = l; naloga uvaja možnost onesnaženja s kupom. Vrednost, ki se ne ujema s parametriziranim tipom parametra varargs l je mogoče dodeliti spremenljivki oArray. Vendar prevajalnik ne ustvari nepreverjenega opozorila, ker je to že storil pri prevajanju Seznam ... l do Seznam [] l. Ta dodelitev je veljavna, ker je spremenljivka l ima tip Seznam [], katere podvrste Predmet [].

Poleg tega prevajalnik pri dodeljevanju a ne izda opozorila ali napake Seznam predmet katere koli vrste kateremu koli od oArraykomponente matrike; na primer, oArray [0] = Arrays.asList (novo Double (3.5));. Ta dodelitev dodeli prvi komponenti polja oArray a Seznam predmet, ki vsebuje en sam java.lang.Dvojnik predmet.

The Niz s = l [0] .get (0); dodelitev je problematična. Predmet, shranjen v prvi komponenti matrike spremenljivke l ima tip Seznam, vendar ta dodelitev pričakuje objekt tipa Seznam. Kot rezultat, JVM vrže java.lang.ClassCastException.

Sestavite to izvorno kodo (javac -Xlint: neoznačeno UnsafeVarargsDemo.java). Pri prevajanju v posodobitvi 6 Java SE 7 upoštevajte naslednje rezultate (nekoliko preoblikovane zaradi berljivosti):

 UnsafeVarargsDemo.java:8: opozorilo: [neoznačeno] nepreverjeno ustvarjanje generičnega polja za parameter varargs tipa List [] nevarno (Arrays.asList ("A", "B", "C"), ^ UnsafeVarargsDemo.java:12: opozorilo : [neoznačeno] Možno onesnaženje kupa s parametriziranim tipom vararg Seznam statičnih praznin nevarno (Seznam ... l) ^ 2 opozorili 

V svojem uvodu Java 101 v generike sem navedel, da v izrazih za ustvarjanje matrike ne morete uporabljati parametrov tipa. Ne morete na primer določiti elementi = novi E [velikost];. Ko to poskusite, prevajalnik sporoči sporočilo "generična napaka pri ustvarjanju polja". Vendar je še vedno mogoče ustvariti generično matriko, vendar le v kontekstu varargs, in o tem poroča prvo opozorilno sporočilo. V zakulisju se prevajalnik preoblikuje Seznam ... l do Seznam [] l in nato do Seznam [] l.

Upoštevajte, da se opozorilo o onesnaženosti kopiči na nevarno () mesto deklaracije metode. To sporočilo ni ustvarjeno na mestu klica te metode, kar velja za prevajalnike Java 5 in 6.

Vse metode varargov ne bodo prispevale k onesnaženju kupa. Kljub temu bo na mestu deklaracije metode še vedno izdano opozorilno sporočilo. Če veste, da vaša metoda ne prispeva k onesnaženju kopice, lahko to opozorilo zatrete tako, da ga prijavite z @SafeVarargs pripis - Java 7 je predstavil java.lang.SafeVarargs vrsta pripisa. Na primer, ker za Polja razredov asList () metoda, ki prispeva k onesnaženju kopnega, je izjava te metode označena z @SafeVarargs, kot sledi:

 @SafeVarargs javni statični seznam asList (T ... a) 

The @SafeVarargs pripis odstrani splošna sporočila o ustvarjanju polja in opozorilu o onesnaženju kopice. Je dokumentiran del pogodbe metode in trdi, da izvedba metode ne bo nepravilno obravnavala formalnega parametra varargs.

V zaključku

Java 7 je izboljšala produktivnost razvijalcev z uvedbo samodejnega upravljanja virov prek izjave »preizkusi z viri« in novega Samodejno zapre vmesnik, vklopni niz, večkratni ulov, končno vračanje, binarni literali, podčrtaji v številskih literalah, spremembe algoritma sklepanja o tipu prevajalnika, ki je uvedel tako imenovani diamantni operater, in poenostavljen klic metode varargs. Naslednji v Java 101: Naslednja generacija series je pregled lambda in funkcijskega vmesnika jezika Java 8.

To zgodbo, "Java 101: Osnovna predstavitev jezikov Java, del 5", je prvotno objavil JavaWorld.

$config[zx-auto] not found$config[zx-overlay] not found