Mam następującą ArrayList
klasę Collection języka Java:
ArrayList<String> animals = new ArrayList<String>();
animals.add("bat");
animals.add("owl");
animals.add("bat");
animals.add("bat");
Jak widać, animals
ArrayList
składa się z 3 bat
elementów i jednego owl
elementu. Zastanawiałem się, czy w ramach Collection istnieje interfejs API, który zwraca liczbę bat
wystąpień, czy też istnieje inny sposób określenia liczby wystąpień.
Odkryłem, że kolekcja Google Multiset
ma interfejs API, który zwraca całkowitą liczbę wystąpień elementu. Ale to jest kompatybilne tylko z JDK 1.5. Nasz produkt jest obecnie w JDK 1.6, więc nie mogę go używać.
Odpowiedzi:
Jestem prawie pewien, że metoda statycznej częstotliwości w Kolekcjach przydałaby się tutaj:
Tak i tak bym to zrobił. Jestem prawie pewien, że to jest jdk 1.6 prosto.
źródło
W Javie 8:
źródło
Collections.frequency()
? Wydaje się mniej czytelne.To pokazuje, dlaczego ważne jest, aby „ Odwołać się do obiektów za pomocą ich interfejsów ”, jak opisano w książce Effective Java .
Jeśli zakodujesz implementację i użyjesz ArrayList w powiedzmy 50 miejscach w swoim kodzie, kiedy znajdziesz dobrą implementację "List", która liczy elementy, będziesz musiał zmienić wszystkie te 50 miejsc i prawdopodobnie będziesz musiał złamać swój kod (jeśli jest używany tylko przez Ciebie, nie ma problemu, ale jeśli jest używany przez kogoś innego, złamiesz też jego kod)
Programując w interfejsie, możesz pozostawić te 50 miejsc bez zmian i zamienić implementację z ArrayList na „CountItemsList” (na przykład) lub inną klasę.
Poniżej znajduje się bardzo podstawowy przykład, jak można to napisać. To tylko próbka, lista gotowa do produkcji byłaby znacznie bardziej skomplikowana.
Zastosowane tu zasady OO: dziedziczenie, polimorfizm, abstrakcja, hermetyzacja.
źródło
Przepraszamy, nie ma prostej metody, która może to zrobić. Wszystko, co musisz zrobić, to stworzyć mapę i policzyć za jej pomocą częstotliwość.
źródło
W Javie nie ma natywnej metody, która mogłaby to zrobić za Ciebie. Możesz jednak użyć IterableUtils # countMatches () z Apache Commons-Collections, aby zrobić to za siebie.
źródło
Właściwie klasa Collection ma statyczną metodę o nazwie: frequency (Collection c, Object o), która zwraca liczbę wystąpień elementu, którego szukasz, nawiasem mówiąc, to zadziała idealnie dla Ciebie:
źródło
Alternatywne rozwiązanie Java 8 wykorzystujące strumienie :
źródło
Zastanawiam się, dlaczego nie możesz używać tego Google Collection API z JDK 1.6. Czy tak jest napisane? Myślę, że możesz, nie powinno być żadnych problemów ze zgodnością, ponieważ jest zbudowany dla niższej wersji. Sprawa wyglądałaby inaczej, gdyby zostały skompilowane dla wersji 1.6 i używasz wersji 1.5.
Czy gdzieś się mylę?
źródło
Może być nieco bardziej wydajne podejście
źródło
Aby uzyskać wystąpienia obiektu bezpośrednio z listy:
Aby uzyskać wystąpienie kolekcji Object inside list, nadpisz metodę equals w klasie Object jako:
Zadzwoń do Collections.frequency jako:
źródło
Prosty sposób na znalezienie wystąpienia wartości ciągu w tablicy przy użyciu funkcji Java 8.
Wynik: {Kot = 2, Koza = 1, Krowa = 1, krowa = 1, Pies = 1}
Możesz zauważyć, że "Krowa" i krowa nie są traktowane jako ten sam ciąg, jeśli potrzebujesz tego z tą samą liczbą, użyj .toLowerCase (). Znajdź poniższy fragment dla tego samego.
Wynik: {kot = 2, krowa = 2, koza = 1, pies = 1}
źródło
toString()
jest niepotrzebna. Możesz po prostu zrobić:duplicateList.stream().collect(Collectors.groupingBy(e -> e,Collectors.counting()));
To, czego chcesz, to torba - która jest jak zestaw, ale liczy również liczbę wystąpień. Niestety framework java Collections - świetny, ponieważ nie ma implantu Bag. W tym celu należy użyć tekstu łącza Apache Common Collection
źródło
Metoda 1:
Metoda 2:
źródło
Jeśli używasz kolekcji Eclipse , możesz użyć pliku
Bag
. AMutableBag
można zwrócić z dowolnej implementacjiRichIterable
przez wywołanietoBag()
.HashBag
Realizacja w Eclipse Kolekcje jest poparteMutableObjectIntMap
.Uwaga: jestem promotorem Eclipse Collections.
źródło
Umieść elementy arraylisty w tablicy mieszania, aby policzyć częstotliwość.
źródło
Java 8 - inna metoda
źródło
Więc zrób to w staromodny sposób i stwórz własny:
źródło
Jeśli jesteś użytkownikiem mojego ForEach DSL , możesz to zrobić za pomocą
Count
zapytania.źródło
Nie chciałem utrudniać tej sprawy i sprawiłem, że za pomocą dwóch iteratorów mam HashMap z LastName -> FirstName. A moja metoda powinna usunąć elementy z dulicate FirstName.
źródło
Wynik:
źródło
źródło
źródło