Útmutató a Java 8 Comparatorhoz. Összehasonlítás ()
1. Áttekintés
A Java 8 számos fejlesztést vezetett be a Összehasonlító interfész, beleértve egy maroknyi statikus funkciót, amelyek nagy hasznát veszik a gyűjtemények rendezési sorrendjének kidolgozásakor.
A Java 8 lambdas hatékonyan kihasználható a Összehasonlító interfész is. A lambdas és a Összehasonlító itt található, valamint egy krónika a Összehasonlító itt található.
Ebben az oktatóanyagban meg fogjuk vizsgálni a Összehasonlító felület a Java 8-ban.
2. Az első lépések
2.1. Mintabab osztály
A cikk példáihoz hozzunk létre egy Munkavállaló babot, és mezőit használja összehasonlítási és rendezési célokra:
public class Alkalmazott {String név; int kor; kettős fizetés; hosszú mobil; // kivitelezők, szerelők és beállítók}
2.2. Tesztelési adataink
Hozzunk létre egy alkalmazotti tömböt is, amelyet a cikkünkben különböző tesztesetekben tárolunk a típusunk eredményei számára:
alkalmazottak = új alkalmazott [] {...};
Az elemek kezdeti rendezése alkalmazottak lesz:
[Alkalmazott (név = John, életkor = 25, fizetés = 3000,0, mobil = 9922001), Alkalmazott (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Alkalmazott (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
A cikkben a fentiek szerint válogatunk Munkavállaló tömb különböző funkciók használatával.
A teszt állításokhoz előre rendezett tömböket használunk, amelyeket összehasonlítunk rendezési eredményeinkkel (azaz alkalmazottak tömb) különböző forgatókönyvekhez.
Nyilatkozjuk néhány ilyen tömböt:
@A nyilvános void előtt initData () {sortedEmployeesByName = new Employee [] {...}; sortedEmployeesByNameDesc = új alkalmazott [] {...}; sortedEmployeesByAge = új alkalmazott [] {...}; // ...}
Mint mindig, a teljes kódot bátran olvassa el a GitHub linkünkön.
3. Használata Összehasonlító.összehasonlítás
Ez a szakasz a Összehasonlító.összehasonlítás statikus függvény.
3.1. Kulcsválasztó variáns
A Összehasonlító.összehasonlítás a statikus függvény elfogad egy rendezési kulcsot Funkció és visszaadja a Összehasonlító a típushoz, amely a rendezési kulcsot tartalmazza:
statikus Összehasonlító összehasonlítás (Function keyExtractor)
Ahhoz, hogy ezt működés közben lássuk, használjuk a név mező ben Munkavállaló rendezési kulcsként, és adja át a metódus hivatkozását típusú argumentumként Funkció. A Összehasonlító ugyanabból visszaküldött rendezésre szolgál:
@Test public void whenComparing_thenSortedByName () {Comparator workerNameComparator = Comparator.comparing (Employee :: getName); Arrays.sort (alkalmazottak, alkalmazottNévKomparátor); assertTrue (tömbök.egyenlő (alkalmazottak, sortedEmployeesByName)); }
Mint láthatja, a alkalmazottak tömb értékek név szerint vannak rendezve a rendezés eredményeként:
[Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
3.2. Kulcsválasztó és Összehasonlító Változat
Van még egy lehetőség, amely megkönnyíti a rendezési kulcs természetes sorrendjének felülírását az Összehasonlító amely egyéni rendezést hoz létre a rendezési kulcshoz:
statikus összehasonlító összehasonlítása (Function keyExtractor, Comparator keyComparator)
Módosítsuk a fenti tesztet, felülírva a rendezés természetes sorrendjét név mezőt a Összehasonlító a nevek csökkenő sorrendbe rendezéséhez a második argumentumként Összehasonlító.összehasonlítás:
@Test public void whenComparingWithComparator_thenSortedByNameDesc () {Comparator workerNameComparator = Comparator.comparing (Employee :: getName, (s1, s2) -> {return s2.compareTo (s1; Arrays.sort (alkalmazottak, alkalmazottNévKomparátor); assertTrue (Tömbök.egyenlő (alkalmazottak, sortedEmployeesByNameDesc)); }
Amint láthatja, az eredményeket csökkenő sorrendben rendezik név:
[Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001)]
3.3. Használata Összehasonlító.fordítva
Amikor létezőre hívják Összehasonlító, a példány metódus Összehasonlító.fordítva egy újat ad vissza Összehasonlító ez megfordítja az eredeti rendezési sorrendjét.
Használjuk a Összehasonlító hogy az alkalmazottakat rendezi név és fordított úgy, hogy az alkalmazottak a név:
@Test public void whenReversed_thenSortedByNameDesc () {Comparator workerNameComparator = Comparator.comparing (Employee :: getName); Comparator workerNameComparatorReversed = alkalmazottNévComparator.reversed (); Arrays.sort (alkalmazottak, alkalmazottNévKomparátorReversed); assertTrue (tömbök.egyenlő (alkalmazottak, sortedEmployeesByNameDesc)); }
Az eredményeket csökkenő sorrendben rendezik név:
[Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001)]
3.4. Használata Comparator.comparingInt
Van egy funkció is Comparator.comparingInt amely ugyanazt teszi, mint Összehasonlító.összehasonlítás, de csak erre van szükség int válogatók. Próbáljuk ki ezt egy példával, ahol megrendeljük alkalmazottak által kor:
@Test public void whenComparingInt_thenSortedByAge () {Comparator workerAgeComparator = Comparator.comparingInt (Employee :: getAge); Arrays.sort (alkalmazottak, alkalmazottAgeComparator); assertTrue (tömbök.egyenlő (alkalmazottak, sortedEmployeesByAge)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezik:
[Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
3.5. Használata Comparator.comparingLong
Hasonló, mint amit tettünk int kulcsokat, nézzünk meg egy példát a Comparator.comparingLong hogy fontoljon egy típusú rendezési kulcsot hosszú megrendelésével a alkalmazottak tömb a Mobil terület:
@Test public void whenComparingLong_thenSortedByMobile () {Comparator workerMobileComparator = Comparator.comparingLong (Employee :: getMobile); Tömbök.sort (alkalmazottak, alkalmazottMobileComparator); assertTrue (Tömbök.egyenlő (alkalmazottak, sortedEmployeesByMobile)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezi Mobil mint kulcs:
[Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401), Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001)]
3.6. Használata Comparator.comparingDouble
Ismét hasonló ahhoz, amit tettünk int és hosszú kulcsokat, nézzünk meg egy példát a Comparator.comparingDouble hogy fontoljon egy típusú rendezési kulcsot kettős megrendelésével a alkalmazottak tömb a fizetés terület:
@Test public void whenComparingDouble_thenSortedBySalary () {Comparator workerSalaryComparator = Comparator.comparingDouble (Employee :: getSalary); Tömbök.sort (alkalmazottak, alkalmazottSalaryComparator); assertTrue (tömbök.egyenlő (alkalmazottak, sortedEmployeesBySalary)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezi fizetés mint rendezési kulcs:
[Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
4. Figyelembe véve a természetes rendet Összehasonlító
A természetes rendet a. Viselkedése határozza meg Hasonló interfész megvalósítása. További információ a különbségről Összehasonlító és felhasználása Hasonló felület megtalálható ebben a cikkben.
Tegyük végre Hasonló miénkben Munkavállaló osztály, hogy kipróbálhassuk a naturalRendelés és fordított sorrendben funkciói Összehasonlító felület:
public class Employee implement Comparable {// ... @Orride public int CompareTo (Employee argEmployee) {return name.compareTo (argEmployee.getName ()); }}
4.1. A természetes rend használata
A naturalRendelés függvény a Összehasonlító az aláírásban említett visszatérési típus esetében:
statikus Természetes összehasonlítóRendelés ()
A fenti logika alapján az alkalmazottak összehasonlítása az alapján név mezőben használjuk ezt a függvényt a Összehasonlító amely rendezi a alkalmazottak tömb természetes sorrendben:
@Test public void whenNaturalOrder_thenSortedByName () {Comparator workerNameComparator = Összehasonlító. naturalRendelés (); Arrays.sort (alkalmazottak, alkalmazottNévKomparátor); assertTrue (tömbök.egyenlő (alkalmazottak, sortedEmployeesByName)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezik:
[Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
4.2. A fordított természetes rend használata
Hasonló naturalRendelés, használjuk a fordított sorrendben módszer a Összehasonlító amelynek fordított sorrendje lesz alkalmazottak a naturalRendelés példa:
@Test public void whenReverseOrder_thenSortedByNameDesc () {Comparator workerNameComparator = Összehasonlító. fordított sorrendben(); Arrays.sort (alkalmazottak, alkalmazottNévKomparátor); assertTrue (tömbök.egyenlő (alkalmazottak, sortedEmployeesByNameDesc)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezik:
[Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001)]
5. A nullértékek figyelembevétele az összehasonlítóban
Ez a szakasz a funkciókat ismerteti nullsElőször és nullsLast, amelyek figyelembe veszik nulla értékek a sorrendben és a nulla értékek a sorrend elején vagy végén.
5.1. Figyelembe véve a Null First-t
Véletlenszerűen szúrjuk be nulla értékek ben alkalmazottak sor:
[Alkalmazott (név = John, életkor = 25, fizetés = 3000,0, mobil = 9922001), null, alkalmazott (név = ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), null, alkalmazott (név = Keith, életkor) = 35, fizetés = 4000,0, mobil = 3924401)]
A nullsElőször függvény visszaadja a Összehasonlító hogy mindent megtart nullák a sorrend elején:
@Test public void whenNullsFirst_thenSortedByNameWithNullsFirst () {Comparator workerNameComparator = Comparator.comparing (Employee :: getName); Összehasonlító alkalmazottNévComparator_nullFirst = Összehasonlító.nullsFirst (alkalmazottNévKomparátor); Arrays.sort (alkalmazottakArrayWithNulls, alkalmazottNévKomparátor_nullFirst); assertTrue (tömbök.egyenlő (alkalmazottakArrayWithNulls, sortedEmployeesArray_WithNullsFirst)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezik:
[null, null, Alkalmazott (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Alkalmazott (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Alkalmazott (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
5.2. Figyelembe véve Null Last
A nullsLast függvény a Összehasonlító hogy mindent megtart nullák a sorrend végén:
@Test public void whenNullsLast_thenSortedByNameWithNullsLast () {Comparator workerNameComparator = Comparator.comparing (Employee :: getName); Comparator workerNameComparator_nullLast = Összehasonlító.nullsLast (alkalmazottNévKomparátor); Arrays.sort (alkalmazottakArrayWithNulls, alkalmazottNévKomparátor_nullLast); assertTrue (tömbök. egyenlő (alkalmazottakArrayWithNulls, sortedEmployeesArray_WithNullsLast)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezik:
[Munkavállaló (név = Ász, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = János, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401), null, null]
6. Használata Összehasonlító.akkor Összehasonlítás
A akkorHasonlítás funkció segítségével beállíthatja az értékek lexikográfiai sorrendjét úgy, hogy több rendezési kulcsot biztosít egy adott sorrendben.
Vegyünk egy másik tömböt Munkavállaló osztály:
someMoreEmployees = new Employee [] {...};
Vegye figyelembe a fenti tömb következő elemeit:
[Munkavállaló (név = Jake, életkor = 25, fizetés = 3000,0, mobil = 9922001), Munkavállaló (név = Jake, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = Ász, életkor = 22, fizetés = 3000,0, mobil = 6423001), alkalmazott (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
Írjuk az összehasonlítások sorozatát kor majd a név és nézze meg ennek a tömbnek a sorrendjét:
@Test public void whenThenComparing_thenSortedByAgeName () {Comparator worker_Age_Name_Comparator = Comparator.comparing (Employee :: getAge) .thenComparing (Employee :: getName); Tömbök.sort (someMoreEmployees, worker_Age_Name_Comparator); assertTrue (tömbök.egyenlő (néhányTöbbEmployees, sortedEmployeesByAgeName)); }
A megrendelést itt végzi el kor, és az azonos értékekkel kor, a megrendelést a név. Figyeljük meg ezt a válogatás után kapott sorrendben:
[Munkavállaló (név = Ász, életkor = 22, fizetés = 3000,0, mobil = 6423001), Munkavállaló (név = Jake, életkor = 22, fizetés = 2000,0, mobil = 5924001), Munkavállaló (név = Jake, életkor = 25, fizetés = 3000,0, mobil = 9922001), alkalmazott (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
Használjuk a másik verzióját akkorHasonlítás vagyis akkorHasonlításInt, a lexikográfiai sorrend megváltoztatásával név utána kor:
@Test public void whenThenComparing_thenSortedByNameAge () {Comparator worker_Name_Age_Comparator = Comparator.comparing (Employee :: getName) .thenComparingInt (Employee :: getAge); Tömbök.sort (someMoreEmployees, worker_Name_Age_Comparator); assertTrue (Tömbök.egyenlő (néhányTöbbEmployees, sortedEmployeesByNameAge)); }
Lássuk, hogyan alkalmazottak a tömb értékeket a rendezés után rendezik:
[Alkalmazott (név = Ász, életkor = 22, fizetés = 3000,0, mobil = 6423001), Alkalmazott (név = Jake, életkor = 22, fizetés = 2000,0, mobil = 5924001), Alkalmazott (név = Jake, életkor = 25, fizetés = 3000,0, mobil = 9922001), alkalmazott (név = Keith, életkor = 35, fizetés = 4000,0, mobil = 3924401)]
Hasonlóképpen vannak funkciók akkorHosszúság összehasonlítása és akkorA kettős összehasonlítása használatra hosszú és kettős válogató kulcsok.
7. Következtetés
Ez a cikk útmutató a Java 8-ban bevezetett számos funkcióhoz Összehasonlító felület.
Szokás szerint a forráskód megtalálható a Githubon.