Java ArrayList vs Vector

áttekintés

ebben az oktatóanyagban az ArrayList és a Vector osztályok közötti különbségekre fogunk összpontosítani. Mindkettő a Java Collections keretrendszerhez tartozik, és implementálja a java-t.util.Lista Felület.

ezeknek az osztályoknak azonban jelentős különbségek vannak a megvalósításukban.

mi a különbség?

gyors kezdésként mutassuk be az ArrayList és a Vector főbb különbségeit. Ezután részletesebben megvitatjuk néhány pontot:

  • szinkronizálás – az első nagy különbség a kettő között.
  • méretnövekedés – egy másik különbség a kettő között az átméretezés módja, miközben elérik a kapacitásukat. A vektor megduplázza méretét. Ezzel szemben az ArrayList csak a hosszának felével növekszik
  • iteráció – és a vektor használhatja az Iterátort és a felsorolást az elemek áthaladásához. Másrészt az ArrayList csak Iterátort használhat.
  • teljesítmény – nagyrészt a szinkronizálásnak köszönhetően a vektor műveletek lassabbak az ArrayList
  • keretrendszerhez képest – az ArrayList a gyűjtemények keretrendszerének része, amelyet a JDK 1.2-ben vezettek be. Eközben a vector a Java korábbi verzióiban régi osztályként van jelen.

Vector

mivel már van egy kiterjesztett útmutató az ArrayList-ről, itt nem fogjuk megvitatni az API-t és a képességeket. Másrészt bemutatunk néhány alapvető részletet a Vektorról.

egyszerűen fogalmazva, egy vektor átméretezhető tömb. Növekszik és zsugorodik, ahogy hozzáadjuk vagy eltávolítjuk az elemeket.

létrehozhatunk egy vektort tipikus módon:

Vector<String> vector = new Vector<>();

az alapértelmezett konstruktor létrehoz egy üres vektort, amelynek kezdeti kapacitása 10.

adjunk hozzá néhány értéket:

vector.add("baeldung");vector.add("Vector");vector.add("example");

végül pedig iteráljuk át az értékeket az Iterátor interfész használatával:

Iterator<String> iterator = vector.iterator();while (iterator.hasNext()) { String element = iterator.next(); // ...}

vagy bejárhatjuk a vektort felsorolással:

Enumeration e = vector.elements();while(e.hasMoreElements()) { String element = e.nextElement(); // ... }

most fedezzük fel néhány egyedi tulajdonságukat mélyebben.

egyidejűség

már említettük, hogy az ArrayList és a vektor különbözik a párhuzamossági stratégiájukban, de nézzük meg közelebbről. Ha belemerülnénk a Vector metódus aláírásaiba, látnánk, hogy mindegyiknek megvan a szinkronizált kulcsszója:

public synchronized E get(int index)

egyszerűen fogalmazva, ez azt jelenti, hogy egyszerre csak egy szál férhet hozzá egy adott vektorhoz.

valójában azonban ezt a műveleti szintű szinkronizálást mindenképpen át kell fedni az összetett műveletek saját szinkronizálásával.

tehát ezzel szemben az ArrayList más megközelítést alkalmaz. Módszerei nincsenek szinkronizálva, és ez az aggodalom osztályokra oszlik, amelyek a párhuzamosságnak szentelik.

például használhatunk CopyOnWriteArrayList vagy gyűjteményeket.synchronizedList, hogy hasonló hatást érjen el a vektorhoz:

vector.get(1); // synchronizedCollections.synchronizedList(arrayList).get(1); // also synchronized

teljesítmény

mint fentebb már tárgyaltuk, a vektor szinkronizálva van, ami közvetlen hatást gyakorol a teljesítményre.

a vektor és az ArrayList műveletek közötti teljesítménykülönbség megtekintéséhez írjunk egy egyszerű JMH benchmark tesztet.

a múltban megvizsgáltuk az ArrayList műveleteinek időbeli összetettségét, ezért adjuk hozzá a vector teszteseteit.

először teszteljük a get () módszert:

@Benchmarkpublic Employee testGet(ArrayListBenchmark.MyState state) { return state.employeeList.get(state.employeeIndex);}@Benchmarkpublic Employee testVectorGet(ArrayListBenchmark.MyState state) { return state.employeeVector.get(state.employeeIndex);}

a JMH-t úgy állítjuk be, hogy három szálat és 10 bemelegítő iterációt használjon.

és jelentsük be a műveletenkénti átlagos időt nanoszekundum szinten:

Benchmark Mode Cnt Score Error UnitsArrayListBenchmark.testGet avgt 20 9.786 ± 1.358 ns/opArrayListBenchmark.testVectorGet avgt 20 37.074 ± 3.469 ns/op

láthatjuk, hogy az ArrayList#get körülbelül háromszor gyorsabban működik, mint a Vector#get.

most hasonlítsuk össze a contains () művelet eredményeit:

@Benchmarkpublic boolean testContains(ArrayListBenchmark.MyState state) { return state.employeeList.contains(state.employee);}@Benchmarkpublic boolean testContainsVector(ArrayListBenchmark.MyState state) { return state.employeeVector.contains(state.employee);}

és nyomtassa ki az eredményeket:

Benchmark Mode Cnt Score Error UnitsArrayListBenchmark.testContains avgt 20 8.665 ± 1.159 ns/opArrayListBenchmark.testContainsVector avgt 20 36.513 ± 1.266 ns/op

mint láthatjuk, a contains() műveletnél a vektor teljesítményideje sokkal hosszabb, mint az ArrayList.

összefoglaló

ebben a cikkben a Java vector és ArrayList osztályai közötti különbségeket vizsgáltuk. Ezenkívül részletesebben bemutattuk a vektor funkciókat is.

mint általában, a cikk teljes kódja elérhető a Githubon.

kezdje el a Spring 5 és a Spring Boot 2 használatát a Learn Spring tanfolyamon keresztül:

>> nézze meg a tanfolyamot



+