Giriş
JSE 5.0-den başlap, Java dil arsenalyna generikler goşuldy.Java-da generikler näme?
Generika (umumylaşdyrma) umumylaşdyrylan programmirlemäni amala aşyrmak üçin Java diliniň aýratyn serişdesidir: maglumatlary we algoritmleri suratlandyrmaga aýratyn çemeleşme, düşündirişini üýtgetmän dürli maglumatlar bilen işlemäge mümkinçilik berýär. Oracle web sahypasynda umumy sapaklara bagyşlanan aýratyn sapak: “ Sapak: Generika ”.
import java.util.*;
public class HelloWorld{
public static void main(String []args){
List list = new ArrayList();
list.add("Hello");
String text = list.get(0) + ", world!";
System.out.print(text);
}
}
Bu kod gowy işlär. Usöne bize gelip, “Salam, dünýä!” Diýen jümläni aýtsalar näme bolar? ýenjildi we diňe Salam gaýdyp bilersiňizmi? Geliň, kod bilen setir bilen baglanyşygy aýyralyň ", world!"
. Has zyýansyz bolup biläýjek ýaly? Inöne aslynda, DÜZGÜN GÖRNÜŞDE ýalňyşlyk alarys : error: incompatible types: Object cannot be converted to String
Esasy zat, biziň sanawymyzda Obýekt görnüşindäki obýektleriň sanawyny saklaýar. String Obýektiň nesli bolany üçin (ähli synplar Java-da Obýektden doly miras galanlygy sebäpli), aç-açan rol oýnamagy talap edýär, biz etmedik. Birleşdirilende, obýektde statiki usul String.valueOf (obj) çagyrylar, netijede Obýektdäki toString usuly diýler. .Agny, sanawymyzda Obýekt bar. Görnüşi ýaly, Obýekt däl-de, belli bir görnüş gerek bolsa, özümiziň kasting görnüşini etmeli bolarys:
import java.util.*;
public class HelloWorld{
public static void main(String []args){
List list = new ArrayList();
list.add("Hello!");
list.add(123);
for (Object str : list) {
System.out.println((String)str);
}
}
}
Şeýle-de bolsa, bu ýagdaýda Sanaw obýektleriň sanawyny kabul edýär, diňe bir String däl, Integer-de saklaýar. Theöne iň erbet tarapy, bu ýagdaýda düzüjiniň nädogry zat görmezligi. Ine, bu ýerde ýerine ýetiriş döwründe ýalňyşlyk alarys (olar ýalňyşyň “Iş wagty” alnandygyny hem aýdýarlar). Erroralňyşlyk bolar: java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String
Razy, iň ýakymly däl. Bularyň hemmesi düzüjiniň emeli intellekt däldigi we programmistiň diýjek bolýan zatlarynyň hemmesini çaklap bilmeýändigi sebäpli. Kompýuteriň haýsy görnüşlerini ulanjakdygymyz hakda has giňişleýin maglumat bermek üçin Java SE 5 umumy önümleri hödürledi . Geliň, düzüjä isleýän zadymyzy aýdyp, wersiýamyzy düzedeliň:
import java.util.*;
public class HelloWorld {
public static void main(String []args){
List<String> list = new ArrayList<>();
list.add("Hello!");
list.add(123);
for (Object str : list) {
System.out.println(str);
}
}
}
Görşümiz ýaly, indi Stringdäki aktýorlara mätäçlik ýok. Mundan başga-da, indi umumylyklary düzýän burç ýaýlar bar. Indi düzüji, sanawa 123 goşmaçany aýyrýançak, synpyň düzülmegine rugsat bermez, sebäbi bu Integer. Ol bize şeýle diýer. Köp adamlar generiklere "sintaktik şeker" diýýärler. Dogry aýdýarlar, sebäbi generikler düzülende hakykatdanam şol bir kastlara öwrüler. Toplanan synplaryň baş koduna seredeliň: el bilen guýmak we generikleri ulanmak bilen:
Çig görnüşler ýa-da çig görnüşler
Generika barada aýdanymyzda, elmydama iki kategoriýa bar: ýazylan görnüşler (Umumy görnüşler) we “çig” görnüşler (çig görnüşler). Çig görnüşler burç ýaýlarynda “kär” görkezmezden görnüşlerdir:<>
" düşünjesi ýa-da görnüş görnüşi bilen baglanyşykly. Galyberse-de, düzüji, sag tarapda <> görüp, baha bellenen üýtgeýjiniň görnüşiniň deklarasiýasynyň ýerleşýän çep tarapyna seredýär. Bu bölümden sag tarapdaky bahanyň haýsy görnüşde ýazylýandygyna düşünýär. Aslynda, çep tarapda umumy görkezilen we sag tarapda görkezilmedik bolsa, düzüjiniň görnüşini görkezip biler:
import java.util.*;
public class HelloWorld{
public static void main(String []args) {
List<String> list = new ArrayList();
list.add("Hello World");
String data = list.get(0);
System.out.println(data);
}
}
Şeýle-de bolsa, bu täze stiliň generikler bilen köne stiliň garyndysy bolar. Bu gaty islenmeýän zat. Aboveokardaky kody düzenimizde habary alarys : Note: HelloWorld.java uses unchecked or unsafe operations
. Aslynda, bu ýerde göwher goşmagyň näme üçin asla zerur däldigi düşnüksiz ýaly. Hereöne bir mysal:
import java.util.*;
public class HelloWorld{
public static void main(String []args) {
List<String> list = Arrays.asList("Hello", "World");
List<Integer> data = new ArrayList(list);
Integer intNumber = data.get(0);
System.out.println(data);
}
}
Radyma düşýär, “ArrayList” -iň kolleksiýany giriş hökmünde alýan ikinji konstruktory hem bar. Aldaw şu ýerde. Göwher sintaksis bolmasa, düzüjiniň aldanýandygyna düşünenok, göwher bilen düşünýär. Şonuň üçin # 1 düzgün : ýazylan görnüşleri ulansak elmydama göwher sintaksisini ulanyň. Otherwiseogsam, çig görnüşi ulanýan ýerimizde ýitirim bolmak howpy abanýar. "Barlanmadyk ýa-da howply amallary ulanýar" gündeligindäki duýduryşlardan gaça durmak üçin ulanylýan usul ýa-da synp barada ýörite bellik görkezip bilersiňiz: @SuppressWarnings("unchecked")
Basyş, basmak, ýagny göni manyda duýduryşlary basmak üçin terjime edilýär. Whyöne näme üçin görkezmegi ýüregiňize düwdüňiz? Birinji düzgüni ýadyňyzdan çykarmaň, belki ýazmagy goşmaly bolarsyňyz.
Umumy usullar
Generikler usullary ýazmaga mümkinçilik berýär. “Oracle” gollanmasynda bu aýratynlyga bagyşlanan aýratyn bölüm bar: “ Umumy usullar ”. Bu gollanmadan sintaksisi ýatda saklamak möhümdir:- burç ýaýlaryň içinde ýazylan parametrleriň sanawyny öz içine alýar;
- ýazylan parametrleriň sanawy yzyna gaýtarylan usuldan öň gidýär.
import java.util.*;
public class HelloWorld{
public static class Util {
public static <T> T getValue(Object obj, Class<T> clazz) {
return (T) obj;
}
public static <T> T getValue(Object obj) {
return (T) obj;
}
}
public static void main(String []args) {
List list = Arrays.asList("Author", "Book");
for (Object element : list) {
String data = Util.getValue(element, String.class);
System.out.println(data);
System.out.println(Util.<String>getValue(element));
}
}
}
Util synpyna seretseňiz, onda iki sany ýazylan usuly görýäris. Görnüş görnüşi bilen, görnüş kesgitlemesini düzüjä gönüden-göni berip bileris ýa-da özümiz kesgitläp bileris. Iki wariant hem mysalda getirilýär. .Eri gelende aýtsak, sintaksis bu hakda pikir etseň gaty mantykly. Usul ýazylanda, umumy usuldan öň umumy kesgitleýäris, sebäbi usuldan soň umumy ulansak, Java haýsy görnüşini ulanmalydygyny bilip bilmez. Şonuň üçin ilki bilen umumy T ulanjakdygymyzy mälim edýäris, soň bolsa bu umumy görnüşi yzyna gaýtararys diýýäris. Elbetde, Util.<Integer>getValue(element, String.class)
ýalňyşlyk bilen şowsuz bolar incompatible types: Class<String> cannot be converted to Class<Integer>
. Typazuw usullaryny ulananyňyzda, görnüşi pozmak barada elmydama ýadyňyzdan çykarmaly dälsiňiz. Bir mysala seredeliň:
import java.util.*;
public class HelloWorld {
public static class Util {
public static <T> T getValue(Object obj) {
return (T) obj;
}
}
public static void main(String []args) {
List list = Arrays.asList(2, 3);
for (Object element : list) {
System.out.println(Util.<Integer>getValue(element) + 1);
}
}
}
Gowy işlär. Onlyöne düzüjiniň diýilýän usulyň Integer görnüşiniň bardygyna düşünýänçä. Konsol çykyşyny aşakdaky setir bilen çalyşalyň: System.out.println(Util.getValue(element) + 1);
thealňyşlygy alýarys: ikilik operatory üçin erbet operand görnüşleri '+', birinji görnüşi: Obýekt, ikinji görnüş: int .agny, görnüşler pozuldy. Düzediji hiç kimiň görnüşini görkezmändigini, görnüşiň Obýekt hökmünde görkezilendigini we kod ýerine ýetirilişiniň ýalňyşlyk bilen şowsuzdygyny görýär.
Umumy görnüşler
Diňe usullary däl, eýsem synplary hem ýazyp bilersiňiz. “Oracle” -yň gollanmasynda muňa bagyşlanan “ Umumy görnüşler ” bölümi bar. Bir mysala seredeliň:public static class SomeType<T> {
public <E> void test(Collection<E> collection) {
for (E element : collection) {
System.out.println(element);
}
}
public void test(List<Integer> collection) {
for (Integer element : collection) {
System.out.println(element);
}
}
}
Bu ýerde hemme zat ýönekeý. Bir synp ulansak, umumy synpyň adyndan soň görkezilýär. Geliň indi esasy usulda bu synpyň mysalyny döredeliň:
public static void main(String []args) {
SomeType<String> st = new SomeType<>();
List<String> list = Arrays.asList("test");
st.test(list);
}
Gowy işlär. Düzediji sanlaryň sanawynyň we setir görnüşiniň ýygyndysynyň bardygyny görýär. Emma generikleri pozup, muny etsek näme etmeli:
SomeType st = new SomeType();
List<String> list = Arrays.asList("test");
st.test(list);
Erroralňyşlygy alarys: java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Integer
erazmagy täzeden ýazyň. Synpda indi umumylyk ýoklugy sebäpli, düzüji Sanawdan geçenimizden bäri, sanaw <Integer> usuly has ýerliklidir. Aalňyşlyk bilen ýykylýarys. Şonuň üçin # 2 düzgün: Bir synp ýazylsa, mydama umumy görnüşini görkeziň .
Çäklendirmeler
Generikada görkezilen görnüşlere çäklendirme ulanyp bileris. Mysal üçin, konteýneriň diňe San hökmünde giriş hökmünde kabul edilmegini isleýäris. Bu aýratynlyk, “Oracle Tutorial” -da “ Çäklendirilen görnüş parametrleri” bölüminde beýan edilýär . Bir mysala seredeliň:import java.util.*;
public class HelloWorld{
public static class NumberContainer<T extends Number> {
private T number;
public NumberContainer(T number) { this.number = number; }
public void print() {
System.out.println(number);
}
}
public static void main(String []args) {
NumberContainer number1 = new NumberContainer(2L);
NumberContainer number2 = new NumberContainer(1);
NumberContainer number3 = new NumberContainer("f");
}
}
Görşüňiz ýaly, umumy görnüşi San synpy / interfeýs we onuň nesilleri hökmünde çäklendirdik. Gyzykly tarapy, diňe bir synpy däl, interfeýsleri hem kesgitläp bilersiňiz. Mysal üçin: public static class NumberContainer<T extends Number & Comparable> {
Generika-da Wildcard düşünjesi bar https://docs.oracle.com/javase/tutorial/java/generics/wildcards.html Olar hem öz gezeginde üç görnüşe bölünýärler:
- Upperokarky çäkli kartoçkalar - < ? belgisini uzadýar
- Çäklendirilmedik kartoçkalar - < ? >
- Aşaky çäklendirilen kartoçkalar - < ? super Integer >
public static class TestClass {
public static void print(List<? extends String> list) {
list.add("Hello World!");
System.out.println(list.get(0));
}
}
public static void main(String []args) {
List<String> list = new ArrayList<>();
TestClass.print(list);
}
Superöne super bilen çalyşsaňyz, hemme zat gowy bolar. Sanawy çykarmazdan ozal bir baha bilen dolduranymyz üçin, bu biziň üçin sarp ediji, ýagny sarp ediji. Şonuň üçin super ulanýarys.
Miras
Generikleriň başga bir üýtgeşik aýratynlygy bar - olaryň mirasy. Generikleriň mirasy "Oracle" gollanmasynda " Generika, miras we aşaky görnüşler " bölüminde beýan edilýär . Esasy zat aşakdakylary ýatda saklamak we durmuşa geçirmekdir. Muny edip bilmeris:List<CharSequence> list1 = new ArrayList<String>();
Miras umumylyklar bilen başgaça işleýär:
List<String> list1 = new ArrayList<>();
List<Object> list2 = list1;
Bu ýerde hem hemme zat ýönekeý. Sanaw <String> <Object> sanawynyň nesli däl, String Obýektiň neslidir.
Jemleýji
Şeýdip, generika ýadymyzy täzeledik. Theirhli güýjünde seýrek ulanylsa, käbir jikme-jiklikler ýatdan çykýar. Bu gysga syn, ýadyňyzy täzelemäge kömek eder diýip umyt edýärin. Has uly netijeler üçin aşakdaky materiallary okamagyňyzy maslahat berýärin:- Uriuri Tkaç: Çig görnüşler - Generika # 1 - Ösen Java
- Miras we umumy giňeldijiler - Generika # 2 - Ösen Java
- Gaýtalanýan görnüşi giňeltmek - Generika # 3 - Ösen Java
- Aleksandr Matorin - Görnüksiz Generika
- Java bilen tanyşlyk. Generika. Kart kartoçkalary | Tehnostream
- O'Reýli: “Java Generics” we ýygyndylar
GO TO FULL VERSION