Reputation: 155
I was trying to solve some programs, I came across this interesting one, where we need to print the highest occurred character n times & likewise for other characters.
Ex: Input string : "please stay hydrated" Output string : "aaaeeettyysplhdr"
I was only able to solve half way, where we print the highest occurred character & the times it has occurred using a HashMap.
public static void repeatedChar(String str) {
char[] chars = str.toCharArray();
Map<Character, Integer> map = new HashMap<>();
for (Character c : chars) {
if (map.containsKey(c)) {
map.put(c, map.get(c) + 1);
} else {
map.put(c, 1);
}
}
//Now To find the highest character repeated
int max = 0;
//setting to a by default
char maxCharacter = 'a';
for (Map.Entry<Character, Integer> entry : map.entrySet()) {
System.out.println("Key = " + entry.getKey() + ": Value " + entry.getValue());
if (max < entry.getValue()) {
max = entry.getValue();
maxCharacter = entry.getKey();
}
}
System.out.println("Max Character = " + maxCharacter + " Max Count : " + max);
}
This currently prints the highest occured character & the number of times that character has occurred. Can someone please let me know how to proceed further? Thanks
Upvotes: 0
Views: 100
Reputation: 16498
In order to get the desired output you need to sort your map by value. But since a hashmap is not meant to be sorted, but accessed fast, you could add all entries to a list and sort the list. Something like:
import java.util.Map.Entry;
import java.util.Comparator;
....
public static void repeatedChar(String str) {
char[] chars = str.toCharArray();
Map<Character, Integer> map = new HashMap<>();
for (Character c : chars) {
if (map.containsKey(c)) {
map.put(c, map.get(c) + 1);
} else {
map.put(c, 1);
}
}
//add map entries to list
List<Entry<Character, Integer>> list = new ArrayList<>(map.entrySet());
//sort entries by value descending
list.sort(Entry.comparingByValue(Comparator.reverseOrder()));
//print
for (Entry<Character, Integer> entry : list) {
for (int i = 0; i < entry.getValue(); i++){
System.out.print(entry.getKey());
}
}
}
and if you fancy a stream approach:
import java.util.Comparator;
import java.util.Map;
import java.util.function.Function;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
....
public static void repeatedCharWithStreams(String str) {
String output =
Pattern.compile("")
.splitAsStream(str)
.collect(Collectors.groupingBy(Function.identity(),Collectors.counting()))
.entrySet().stream()
.sorted(Map.Entry.comparingByValue(Comparator.reverseOrder()))
.map(e -> e.getKey().repeat(e.getValue().intValue()))
.collect(Collectors.joining());
System.out.println(output);
}
Upvotes: 2