Reputation: 81
From following list I need only 'wow' and 'quit'.
List<String> list = new ArrayList();
list.add("test");
list.add("test");
list.add("wow");
list.add("quit");
list.add("tree");
list.add("tree");
Upvotes: 6
Views: 9401
Reputation: 21
You can use Java 8 Stream api feature to create different list with only unique elements from original list. Please see below code for reference.
List<String> list = new ArrayList<>();
list.add("test");
list.add("test");
list.add("wow");
list.add("quit");
list.add("tree");
list.add("tree");
List<String> uniqueElements = list.stream().filter(element-
>Collections.frequency(list,element)==1).toList();
Above code will initialize 'uniqueElements' list with unique elements from 'list'.
Upvotes: 0
Reputation: 47
Easily clean a list using a lambda:
list.removeIf(element -> Collections.frequency(list, element) > 1);
Upvotes: 1
Reputation: 21
List aList = Arrays.asList("test", "test", "wow", "wow", "wow");
Set hashSet = new HashSet(aList);
hashSet.addAll(aList);
now you can print HashSet all the duplicates values removed
Upvotes: 1
Reputation: 6686
If you're open to using a third-party library, the following can be used with Eclipse Collections:
List<String> list = Arrays.asList("test", "test", "wow", "quit", "tree", "tree");
Set<String> set = Bags.mutable.withAll(list).selectUnique();
System.out.println(set);
Outputs:
[wow, quit]
You can also construct a Bag
directly instead of creating a List
as follows:
MutableBag<String> bag =
Bags.mutable.with("test", "test", "wow", "quit", "tree", "tree");
MutableSet<String> set = bag.selectUnique();
Note: I am a committer for Eclipse Collections
Upvotes: 0
Reputation: 34460
Here is a Java 8 way without streams:
Map<String, Long> counts = new HashMap<>();
list.forEach(word -> counts.merge(word, 1L, Long::sum));
counts.values().removeIf(count -> count > 1);
This first iterates the list and stores the frequency of each word in the counts
map. For this I'm using the Map.merge
method, which either associates the provided value (1L
in this case) with the given key (word
here) or uses the provided merge function (Long::sum
) to combine an existent value with the given one.
Then, words with a frequency greater than 1
are removed from the map via the Collection.removeIf
method.
The whole process has O(n)
time complexity.
Upvotes: 2
Reputation: 311163
@ROMANIA_Engineer's solution should work just fine, but it does hide an O(n2) complexity in it, since Collections.frequency
is an O(n) operation.
A more efficient solution that can still be squeezed in to a single statement could be to count how many times each item occurs and filter just items that appear once:
list.stream()
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting()))
.entrySet()
.stream()
.filter(e -> e.getValue() == 1L)
.map(Map.Entry::getKey)
.forEach(System.out::println);
Upvotes: 1
Reputation: 56626
Java 8+
list.stream() // Stream
.filter(i -> Collections.frequency(list, i) == 1) // Stream
.collect(Collectors.toList()) // List
.forEach(System.out::println); // void
It prints every element from that list that appears exactly once.
Details:
Upvotes: 1
Reputation: 2848
You can use HashMap impl to count occurences and select only onces that occur once.
e.g.
void check(List<String> list)
{
Map<String,Integer> checker = new HashMap<String,Integer>();
List<String> result = new ArrayList<String>();
for(String value: list)
{
Integer count = checker.get(value);
if (count==null)
{
count = 0;
}
checker.put(value, ++count);
}
// now select only values with count == 1
for(String value: checker.keySet())
{
if (checker.get(value) == 1)
{
result.add(value);
}
}
System.out.println(result);
}
Upvotes: 3
Reputation: 46408
you can check the frequency of an element in the Collection and rule out the elements which have frequency higher than 1.
List<String> list = new ArrayList<String>();
list.add("test");
list.add("test");
list.add("wow");
list.add("quit");
list.add("tree");
list.add("tree");
for(String s: list){
if(Collections.frequency(list, s) == 1){
System.out.println(s);
}
Output:
wow
quit
Upvotes: 8
Reputation: 3400
And a Third way
List result = new ArrayList();
for(Object o : list){
if(list.indexOf(o) == list.lastIndexOf(o))
result.add(o);
}
Upvotes: 2
Reputation: 13196
This snippet should leave you with a set (output
) which contains only non-duplicated elements of your list.
HashSet<String> temp = new HashSet<String>();
HashSet<String> output = new HashSet<String>();
for (String element : list)
{
if (temp.contains(element)) output.remove(element);
else
{
temp.insert(element);
output.insert(element);
}
}
Operates in O(n*log(n)) time: one set of logarithmic operations (set lookups, inserts, etc) for each of the n elements in the list.
Upvotes: 4