I have an ArrayList
with the following strings;
List<String> e = new ArrayList<String>();
e.add("123");
e.add("122");
e.add("125");
e.add("123");
I want to check the list for duplicates and remove them from the list. In this case my list will only have two values, and in this example it would be the values 122 and 125, and the two 123s will go away.
What will be the best way to this? I was thinking of using a Set
, but that will only remove one of the duplicates.
If you are going for set then you can achieve it with two sets. Maintain duplicate values in the other set as follows:
In Java 8 you can do:
If !Java 8 you can create a
HashMap<String, Integer>
. If the String already appears in the map, increment its key by one, otherwise, add it to the map.For example:
Now let's assume that you have "123" again, you should get the count of the key and add one to it:
Now you can easily iterate on the map and create a new array list with keys that their values are < 2.
References:
ArrayList#removeIf
Collections#frequency
HashMap
The simplest solutions using streams have
O(n^2)
time complexity. If you try them on aList
with millions of entries, you'll be waiting a very, very long time. AnO(n)
solution is:Here, I used a
LinkedHashMap
to maintain the order. Note that static imports can simplify thecollect
part.This is so complicated that I think using
for
loops is the best option for this problem.I'm a fan of the Google Guava API. Using the Collections2 utility and a generic Predicate implementation it's possible to create a utility method to cover multiple data types.
Thinking about this a bit more
Most of the other examples in this page are using the java.util.List API as the base Collection. I'm not sure if that is done with intent, but if the returned element has to be a List, another intermediary method can be used as specified below. Polymorphism ftw!
Here is a non-Java 8 solution using a map to count occurrences:
You can also use
filter
in Java 8