TEJENDRA PATEL
TEJENDRA PATEL

Reputation: 31

Key missing in TreeSet

I'm adding the hashMap key to one by one in treeSet and try to sort them based on comparator passed in lambda in treeSet.

Without comparator, it is working fine based on default TreeSet.

String s = "tree";
        Map<Character, Integer> freqMap = new HashMap<Character,Integer>();
        for(char ch:s.toCharArray()){
            freqMap.put(ch,freqMap.getOrDefault(ch,0)+1);
        }
        // need to sort TreeSet key with frequency wise
        TreeSet<Character> sortByFreq = new TreeSet<Character>((a,b)->freqMap.get(b).intValue() - freqMap.get(a).intValue());
        for(char ch :freqMap.keySet()){
            System.out.println("from HashMap "+ch);
            sortByFreq.add(ch);
            System.out.println("after adding "+ch+" Treeset like "+sortByFreq);

        }
        System.out.println(freqMap.keySet());
        System.out.println(sortByFreq);

Missing some key in treeSet. What am I doing wrong in treeSet?

O/P

from HashMap r
after adding r Treeset like [r]
from HashMap t
after adding t Treeset like [r]
from HashMap e
after adding e Treeset like [e, r]
[r, t, e]
[e, r]

Upvotes: 3

Views: 190

Answers (1)

Eran
Eran

Reputation: 393836

Your sorting criteria for the TreeSet also defines which elements are considered equal to each other. This means two keys with the same frequency in freqMap will be deemed equal, so only one of them will be added to the Set.

If you want to have all the keys in the TreeSet, you should add to your Comparator a tie-breaker logic, to define the order of two characters having the same frequency.

TreeSet<Character> sortByFreq = new TreeSet<Character>((a,b)->{
                                                          int diff = Integer.compare(freqMap.get(b),freqMap.get(a)); 
                                                           return diff == 0 ? Character.compare(b,a) : diff;
                                                      });

Now the output will be:

[e, t, r]

EDIT:

Or, as Andreas suggested:

TreeSet<Character> sortByFreq = new TreeSet<Character>(Comparator.comparing((Character c) -> freqMap.get(c))
                                                                 .thenComparing(Comparator.naturalOrder())
                                                                 .reversed());

Upvotes: 4

Related Questions