Mówiąc o klasie LinkedHashSet w Javie, musimy wspomnieć, że implementuje ona interfejs Set . LinkedHashSet tworzy kolekcję, która przechowuje elementy w tabeli skrótów, ale zachowuje kolejność wstawiania elementów w przeciwieństwie do swojego odpowiednika HashSet .

Co jest ustawione w Javie

Przypomnijmy pokrótce, że interfejs Set definiuje zbiór (zbiór). Rozszerza Collection i definiuje zachowanie kolekcji, które nie zezwalają na powielanie elementów. Zatem metoda add() zwraca wartość false , jeśli podjęto próbę dodania zduplikowanego elementu do zbioru. Interfejs nie definiuje własnych dodatkowych metod. Interfejs Set dba o unikalność przechowywanych obiektów, o unikalności decyduje implementacja metody equals() . Dlatego jeśli obiekty tworzonej klasy będą dodawane do Set , pożądane jest przesłonięcie metody equals() .

Klasa LinkedHashSet

Zanim zaczniemy mówić o klasie LinkedHashSet , musimy wspomnieć o jej bliskim krewnym, klasie HashSet . HashSet implementuje interfejs Set . Tworzy kolekcję, która przechowuje elementy w tablicy skrótów. Elementy tablicy skrótów są przechowywane jako pary klucz-wartość. Klucz określa komórkę (lub segment) do przechowywania wartości. Zawartość klucza służy do określenia unikalnej wartości zwanej kodem skrótu. Możemy myśleć o kodzie skrótu jako o identyfikatorze obiektu, chociaż nie musi on być unikalny. Ten kod skrótu służy również jako indeks, w którym przechowywane są dane powiązane z kluczem. Klasa LinkedHashSet Java rozszerza HashSet bez dodawania nowych metod .LinkedHashSet pozwala szybko sprawdzić istnienie wpisu, podobnie jak HashSet , ale zawiera uporządkowaną listę wewnątrz. Oznacza to, że przechowuje kolejność wstawiania elementów. Innymi słowy, LinkedHashSet utrzymuje połączoną listę elementów zestawu w kolejności, w jakiej zostały wstawione. Pozwala to na uporządkowaną iterację wstawiania do zestawu. Powoduje to jednak, że klasa LinkedHashSet wykonuje operacje dłużej niż klasa HashSet .

Ważne funkcje LinkedHashSet

  • Unikalne elementy możemy przechowywać tylko w LinkedHashSet

  • LinketHashSet pozwala nam wyodrębniać elementy w tej samej kolejności, w jakiej je wstawiamy

  • LinkedHashSet nie jest zsynchronizowany

  • LinkedHashSet umożliwia przechowywanie elementów zerowych

  • LinkedHashSet wykorzystuje technikę mieszania do przechowywania elementów w określonym indeksie na podstawie kodu mieszania

Metody LinkedHashSet

Oprócz metod odziedziczonych po klasach nadrzędnych, HashSet definiuje następujące metody:
  • boolean add(Object o) dodaje określony element do tego zestawu, jeśli jeszcze go nie ma.

  • void clear() usuwa wszystkie elementy z tego zestawu.

  • Object clone() zwraca pobieżną kopię tej instancji LinkedHashSet : same elementy nie są klonowane.

  • logiczna zawiera(Obiekt o) zwraca wartość true, jeśli ten zestaw zawiera określony element.

  • boolean isEmpty() zwraca wartość true , jeśli ten zestaw nie zawiera żadnych elementów.

  • Iterator iterator() zwraca iterator po elementach tego zestawu.

  • boolean remove(Object o) usuwa określony element z tego zestawu, jeśli jest obecny.

  • int size() zwraca liczbę elementów w tym zestawie (jego liczbę elementów).

Przykłady Easy LinkedHashSet W poniższym przykładzie pokazujemy inicjalizację obiektu LinkedHashSet i użycie metody add() do wypełnienia zestawu.

import java.util.LinkedHashSet;
import java.util.Set;

   public class LinkedHashSetEx1 {
       public static void main(String[] args) {
//LinkedHashSet() Init            
Set<String> set = new LinkedHashSet<>();
//adding elements to LinkedHashSet 
           set.add("Re"); //first added element 
           set.add("Do");
           set.add("Fa");
           set.add("Sol");
           set.add("La");
           set.add("Ti");
           set.add("Mi");//last added element  


           System.out.println(set);
       }
   }
Dane wyjściowe to:
[Re, Do, Fa, Sol, La, Ti, Mi]
Jak widać elementy w naszym zestawie pojawiły się w tej samej kolejności, w jakiej je umieściliśmy. LinkedHashSet w Javie - 1

Przykład 2. Dodanie duplikatu do LinkedHashSet

Wstawmy ponownie nasze elementy LinkedHashSet 7 z nazwami partytur muzycznych i wstawmy jeden nowy element, który jest taki sam jak jeden z elementów umieszczonych wcześniej.

import java.util.LinkedHashSet;
import java.util.Set;

public class LinkedHashSetEx2 {
   public static void main(String[] args) {
           Set<String> set = new LinkedHashSet<>();
           set.add("Re");
           set.add("Do");
           set.add("Fa");
           set.add("Sol");
           set.add("La");
           set.add("Ti");
           set.add("Mi");
           set.add("Sol");
           System.out.println(set);
       }
   }
Wyjście programu jest tutaj:
[Re, Do, Fa, Sol, La, Ti, Mi]
Dane wyjściowe z przykładu drugiego są dokładnie takie same jak w przykładzie pierwszym. Nie możemy mieć dwóch podobnych elementów w kolekcji LinkedHashSet . Kiedy próbujemy umieścić drugi, jest on po prostu ignorowany.

Przykład 3. Usuwanie elementów z LinkedHashSet


import java.util.LinkedHashSet;
import java.util.Set;
   public class LinkedHashSet3 {
       public static void main(String[] args) {
           Set<String> set = new LinkedHashSet<>();
           set.add("Re");
           set.add("Do");
           set.add("Fa");
           set.add("Sol");
           set.add("La");
           set.add("Ti");
           set.add("Mi");
           System.out.println(set);
           set.remove("Fa");// removing an element from our set
           set.remove("Score");//trying to remove element that isn't in set
           System.out.println(set.remove("Score"));
           System.out.println("Print our set without elements removed: ");
           System.out.println(set);
           set.clear();
           System.out.println("Print out our set after clear command: ");
           System.out.println(set);
       }
   }
Wyjście programu jest tutaj:
[Re, Do, Fa, Sol, La, Ti, Mi] false Wydrukuj nasz zestaw bez usuniętych elementów: [Re, Do, Sol, La, Ti, Mi] Wydrukuj nasz zestaw po wyraźnym poleceniu: []
Jak widać, metoda remove() zastosowana do nieistniejącego elementu nie powoduje błędu programu. Po prostu zwraca false , jeśli element nie został usunięty, i true , jeśli element był w LinkedHashSet , a następnie został usunięty.

LinkedHashSet vs HashSet

Te dwie klasy są bliskimi krewnymi. Jednak wewnątrz HashSet używa HashMap do przechowywania obiektów, podczas gdy LinkedHashSet używa LinkedHashMap . Jeśli nie musisz utrzymywać kolejności wstawiania, ale musisz przechowywać unikalne obiekty, bardziej odpowiednie jest użycie HashSet . Jeśli chcesz zachować kolejność wstawiania elementów, wybierz LinkedHashSet . Wydajność LinkedHashSet jest nieco wolniejsza niż HashSet , ponieważ LinkedHashSet używa wewnętrznego LinkedList do zachowania kolejności wstawiania elementów. Weźmy przykład:

import java.util.*;

public class LinkedHashSetExample1 {

   public static void main(String[] args) {
       // while regular hash set orders its elements according to its hashcode stamps

       Set<Integer> regularHashSet = new HashSet<>();
       regularHashSet.add(7);
       regularHashSet.add(3);
       regularHashSet.add(5);
       regularHashSet.add(65536);
       regularHashSet.add(9);
       // few duplicates
       regularHashSet.add(5);
       regularHashSet.add(7);

       // next will print:
       // > regularHashSet = [65536, 3, 5, 7, 9]
       System.out.println("regularHashSet = " + regularHashSet);

       // linked hash set keeps order of adding unchanged

       Set<Integer> linkedHashSet = new LinkedHashSet<>();
       linkedHashSet.add(7);
       linkedHashSet.add(3);
       linkedHashSet.add(5);
       linkedHashSet.add(65536);
       linkedHashSet.add(9);
       // few duplicates
       linkedHashSet.add(5);
       linkedHashSet.add(7);

       // next will print:
       // > linkedHashSet = [7, 3, 5, 65536, 9]
       System.out.println("linkedHashSet = " + linkedHashSet);
   }
}
Wyjściem programu jest:
regularny zestaw Hash = [65536, 3, 5, 7, 9] połączony zestaw Hash = [7, 3, 5, 65536, 9]

Używanie Java LinkedHashSet w rzeczywistych aplikacjach

Ponieważ LinkedHashSet pozwala szybko sprawdzić istnienie wpisu, a także przechowuje kolejność, ta kolekcja wydaje się być całkiem wygodna do usuwania duplikatów z listy. Lub na przykład rozwiązywanie problemów, takich jak ostatnio widziana rzecz w mojej torbie. Lub pamiętasz taką grę, Pokemon Go? LinkedHashSet może przechowywać listę Pokémonów, które napotkałeś, oraz kolejność, w jakiej napotkałeś je na swojej ścieżce. W takim przypadku „powtórzony” Pokémon nie będzie już dodawany do listy. Lub na przykład lista bossów według poziomu, których spotkałeś już w dowolnej grze z poziomami. Albo historia odkrycia ciał kosmicznych. LinkedHashSetpozwala szybko sprawdzić, czy bryła pomieszczenia znajduje się już na liście, a jeśli jej tam nie ma, to dodać ją do listy. Weźmy przykład eliminowania duplikatów.

import java.util.*;

class LinkedHashSetExample2 {
   public static void main(String[] args) {
       List<String> listWithDuplicates = List.of("some","elements","with", "few", "duplicates", "were", "here", "duplicates", "duplicates");

       Set<String> linkedHashSet = new LinkedHashSet<>(listWithDuplicates);
       List<String> listWithoutDuplicates = new ArrayList<>(linkedHashSet);

       // next will print:
       // > listWithDuplicates = [some, elements, with, few, duplicates, here, duplicates, duplicates]
       System.out.println("listWithDuplicates = " + listWithDuplicates);
       // next will print:
       // > listWithoutDuplicates = [some, elements, with, few, duplicates, here]
       System.out.println("listWithoutDuplicates = " + listWithoutDuplicates);

       // -------------------------------------------------------------------------

       // while using regular Hash Set will generally produces some unexpected order
       Set<String> regularHashSet = new HashSet<>(listWithDuplicates);

       // next will print:
       // > linkedHashSet = [some, elements, with, few, duplicates, were, here]
       System.out.println("linkedHashSet = " + linkedHashSet);
       // next will print:
       // > regularHashSet = [here, some, with, duplicates, were, elements, few]
       System.out.println("regularHashSet = " + regularHashSet);
   }
}
Wyjście programu jest tutaj:
listWithDuplicates = [niektóre elementy, z, kilka, duplikaty, były, tutaj, duplikaty, duplikaty] listWithoutDuplicates = [niektóre, elementy, z, kilka, duplikaty, były tutaj] linkedHashSet = [niektóre, elementy, z, kilka, duplikaty , były, tutaj] regularHashSet = [tutaj, niektóre, z, duplikaty, były, elementy, kilka]