Kom-pa-TI-bilitet
Java: enkel fråga om Generics
Visa signatur
Skrivet av Teknocide:
Det som jag inte riktigt förstått är varför man bör ange <String> vid ArrayList()-instansieringen. Variabeln myList är ju den referens som håller objektet så vad är det egentliga värdet av att skriva ... = new ArrayList<String>() istället för new ArrayList()?
Jag gissar lite nu, men:
Att inte ange <String> leder ju till en varning. Alternativet skulle vara att inte varna vid följande tillfälle:
List foo = new ArrayList<Integer>();
foo.add(5);
List<String> bar = foo; // Ungefär som "bar = ArrayList()"
såvida det inte skulle vara olika typ-varningar vid instantieringar av typen Type var = new Type() jämfört med Type var = otherVar. (Och hur praktiskt detta skulle vara känner jag ej till.)
Visa signatur
Vill du ha svar? Citera mig gärna.
Citera flera
Citera
Skrivet av lajnold:
Jag gissar lite nu, men:
Att inte ange <String> leder ju till en varning. Alternativet skulle vara att inte varna vid följande tillfälle:
List foo = new ArrayList<Integer>();
foo.add(5);
List<String> bar = foo; // Ungefär som "bar = ArrayList()"
såvida det inte skulle vara olika typ-varningar vid instantieringar av typen Type var = new Type() jämfört med Type var = otherVar. (Och hur praktiskt detta skulle vara känner jag ej till.)
Hm, NetBeans ger inga varningar för mig, men jag har på känn att Eclipse skulle göra det..
Vad jag menar är att all type-checking sker via myList-variabeln. I ditt exempel så är foo en lista av Object. Koden
List foo = new ArrayList<Integer>();
foo.add(42);
Integer i = foo.get(0);
ger mycket riktigt RuntimeError då man försöker tilldela Object till Integer utan cast.
Min fråga gäller det omvända exemplet: List<String> myList = ... säger klart och tydligt att Listan myList bara tar emot Strings, så var i ligger värdet att deklarera ArrayList-en som <String>? Mitt första exempel kompilerar och körs utan problem.
edit: jag läste om ditt exempel och har lite bättre koll på vad du menar. För att förtydliga vad jag menar så ponera följande:
List<String> foo = new ArrayList<String>();
foo.add("Hello");
List bar = foo;
bar.add(42);
Detta är också kompilerande, körbar kod, trots att foo har deklarerats med ArrayList<String> specifikt. Det är delen ... <String> foo = ... som är signifikant; att ArrayList är av typ String verkar inte betyda någonting.
Senast redigerat
Visa signatur
Kom-pa-TI-bilitet
Citera flera
Citera
Mitt nått gammalt eclipse projekt gav varningar när jag öppnade det senare, just på detta, vet inte om det beror på java versionen man använder, men helt klart bäst att köra på nyare sättet tycker jag, dvs ange typ på alla ställen.
Citera flera
Citera
Citat:
Min fråga gäller det omvända exemplet: List<String> myList = ... säger klart och tydligt att Listan myList bara tar emot Strings, så var i ligger värdet att deklarera ArrayList-en som <String>? Mitt första exempel kompilerar och körs utan problem.
Det är väl förmodligen helt enkelt så att javakompilatorn inte har den finessen i sig. I en tilldelning behöver ju vänsterledet vara av samma typ som (eller en basklass till) högerledet, men om man skriver
List<String> list = new ArrayList();
...så är ju detta ekvivalent med
List<String> list = new ArrayList<Object>();
Typkonflikten är ju då rätt uppenbar.
Naturligtvis hade man ju kunnat bygga kompilatorn så att den behandlar den första deklarationen som ett specialfall och implicit trixar och fixar, men det har inte gjorts.
Man kan komma runt problemet med att skriva samma sak två gånger ändå, genom att utnytta den begränsade typinferens man kan få genom statiska metoder. (Idén är inte min egen, utan snodd från den utmärkta boken Effective Java.) Säg att vi någonstans skulle ha följande:
Map<String, List<Integer>> myMap = new HashMap<String, List<Integer>>();
Om vi definierar en statisk metod newHashMap() enligt:
static <K,V> Map<K,V> newHashMap() { return new HashMap<K,V>(); }
...så kan vi ändra ovanstående deklaration till:
Map<String, List<Integer>> myMap = newHashMap();
Det gör koden lite mer lättläst. Man kan lätt skapa en massa sådana smidiga newWhatever-metoder i en liten utilityklass (säg att den får namnet com.foo.CollectionUtil) och göra importen
import static com.foo.CollectionUtil.*;
...så behöver man bara skriva newWhatever() och inte CollectionUtil.newWhatever() när man vill använda dem.
Citat:
Hm, NetBeans ger inga varningar för mig
Det går att ställa in via Tools->options->editor->hints->standard javac warnings ("unchecked" och "raw types").
Citera flera
Citera
Hårdvara
- Idag Intel Arc får prestandalyft på 300 procent i Assassin's Creed: Unity 13
- Idag Sony läcker uppgifter i rättegång – så stort är Call of Duty 18
- Igår Nvidia: "Energieffektiva RTX 4060 sparar hundralappar" 39
- Igår MSI Geforce RTX 4060 Ventus 2X OC – bra prestanda vid 1080p men medioker kylare 67
- Igår Noctua släpper monteringsram för "deliddade" Ryzen 7000-processorer 15
Mjukvara
Övrigt
Datorkomponenter
System
- Hej, min fjärrkontroll till Google tv'n har pajat och kan inte synka kontrollen
- Bärbar dator för studier och enklare spel för fattig student - förslag i tråden.
- Köpråd för bärbar dator för 3D-arbete (Maya, Zbrush, Substance Designer, Houdini samt Unreal Engine)
- Köpråd: Laptop för spelande - stram budget
- Speldator 15-18k
Ljud, bild och kommunikation
- Diablo IV – den stora tråden2709
- 4G router med simkort1
- Benify-erbjudanden på Samsung-TV [utbruten tråd]1033
- Youtube testar aggressiv taktik mot annonsblockerare90
- Paypal vill ersätta lösenord med passkeys2
- Veckans fråga: Vilket operativsystem föredrar du?120
- Problem att ansluta till mysql via tjänst vid boot.2
- Hej, min fjärrkontroll till Google tv'n har pajat och kan inte synka kontrollen6
- Lagringsdisk - SSD eller HDD 2023?4
- funderade på att köpa ett nytt system: amd eller intel?17
- Säljes 2x Noctua NF-A14 Industrial PPC 2000rpm pwm chromax
- Säljes Switchar, RAM och vattenkylning
- Säljes Intel i5 9400f LGA1151-2
- Säljes Meta Quest 2 VR portabelt headset
- Säljes Komplett dator: Ryzen 7 3700x, GTX1080, 32GB DDR4, 1TB M.2 SSD + 1,5TB HDD, 750W PSU mm. Kan säljas med/utan GPU.
- Säljes Intel Core i5 13400F
- Säljes Gamingdator 4080 / 13700KF / 32GB DDR5
- Säljes I5 12500
- Säljes LG 27'' UltraGear 27GP950 4K Nano IPS 160 Hz HDMI 2.1
- Säljes Star Wars Jedi AMD kod
- Paypal vill ersätta lösenord med passkeys2
- Intel Arc får prestandalyft på 300 procent i Assassin's Creed: Unity13
- Youtube testar aggressiv taktik mot annonsblockerare90
- Sony läcker uppgifter i rättegång – så stort är Call of Duty18
- Nvidia: "Energieffektiva RTX 4060 sparar hundralappar"39
- MSI Geforce RTX 4060 Ventus 2X OC – bra prestanda vid 1080p men medioker kylare67
- Veckans fråga: Vilket operativsystem föredrar du?120
- Bilar med smarta inslag ger fler dumma fel78
- Noctua släpper monteringsram för "deliddade" Ryzen 7000-processorer15
- Nvidias nästa arkitektur för Geforce kommer år 202558
Externa nyheter
Spelnyheter från FZ
- Till slut – Football Manager-saves kommer kunna användas i nyare spel idag
- Quiz – Vad kan du om spöken? idag
- Dying Light 2-uppdatering i dag gör nätterna betydligt farligare idag
- Microsofts vd ser gärna att konsolexklusiviteter försvinner idag
- Bloober Team säger sig vara färdiga med psykologisk skräck idag