Add operation in Scala Vs Java 8

How to perform the Scala operation below to find the most frequent character in a string in java 8?

val tst = "Scala is awesomestttttts" val op = tst.foldLeft(Map[Char,Int]())((a,b) => { a+(b -> ((a.getOrElse(b, 0))+1)) }).maxBy(f => f._2) 

Here is the conclusion

 (Char, Int) = (t,6) 

I managed to get the character stream in Java 8 as follows:

 Stream<Character> sch = tst.chars().mapToObj(i -> (char)i); 

but unable to figure out which fold / foldLeft / foldRight option we have in Java 8

Can anyone help?

+5
source share
3 answers

Something like this is similar to the Scala code you provided (if I understand it correctly):

 String tst = "Java is awesomestttttts"; Optional<Map.Entry<Character, Long>> max = tst.chars() .mapToObj(i -> (char) i) .collect(Collectors.groupingBy(Function.identity(), Collectors.counting())) .entrySet() .stream() .max(Comparator.comparing(Map.Entry::getValue)); System.out.println(max.orElse(null)); 
+8
source

If you do not mind using the third-party Eclipse Collection library, Bag type that can track the number of characters. I have given two examples below that use Bags. Unfortunately, today there is no maxByOccurrences on Bag , but the same result can be achieved using topOccurrences(1) , which is available. You can also use forEachWithOccurrences to search for max, but that will be a bit more code.

The following example uses the CharAdapter , which is also included in the Eclipse collection.

 MutableBag<Character> characters = CharAdapter.adapt("Scala is awesomestttttts") .collect(Character::toLowerCase) .toBag(); MutableList<ObjectIntPair<Character>> charIntPairs = characters.topOccurrences(2); Assert.assertEquals( PrimitiveTuples.pair(Character.valueOf('t'), 6), charIntPairs.get(0)); Assert.assertEquals( PrimitiveTuples.pair(Character.valueOf('s'), 5), charIntPairs.get(1)); 

The second example uses the chars() method, available in String , which returns an IntStream . It feels a little uncomfortable that something called chars () does not return CharStream, but that is because CharStream not available in JDK 8.

 MutableBag<Character> characters = "Scala is awesomestttttts" .toLowerCase() .chars() .mapToObj(i -> (char) i) .collect(Collectors.toCollection(Bags.mutable::empty)); MutableList<ObjectIntPair<Character>> charIntPairs = characters.topOccurrences(2); Assert.assertEquals( PrimitiveTuples.pair(Character.valueOf('t'), 6), charIntPairs.get(0)); Assert.assertEquals( PrimitiveTuples.pair(Character.valueOf('s'), 5), charIntPairs.get(1)); 

In both examples, I first converted the characters to lowercase, so there are 5 occurrences of 's'. If you want uppercase and lowercase letters to be legible, just drop the lowercase code in both examples.

Note: I am a committer for Eclipse collections.

+8
source

Here is an example thread in AbacusUtil :

 String str = "Scala is awesomestttttts"; CharStream.from(str).boxed().groupBy(t -> t, Collectors.counting()) .max(Comparator.comparing(Map.Entry::getValue)).get(); 

But I think the easiest way from Multiset:

 CharStream.from(str).toMultiset().maxOccurrences().get(); 
0
source

Source: https://habr.com/ru/post/1243492/


All Articles