我有一个单词列表(编程语言),我想弄清楚这些单词中字母表中的哪个字母,然后将这些单词的总字符串长度相加,最后返回一个字母返回与这些单词匹配的最长字符串。这是我到现在为止所得到的,而且我几乎没有进一步发展。
这是我尝试更好地理解java流的练习。
package com.example;
import org.junit.Test;
import java.util.ArrayList;
import java.util.List;
import java.util.function.Supplier;
import java.util.stream.IntStream;
import java.util.stream.Stream;
public class DemoApplicationTests {
@Test
public void argh() {
List<String> list = new ArrayList<>();
list.add("java");
list.add("php");
list.add("python");
list.add("perl");
list.add("c");
list.add("lisp");
list.add("c#");
Supplier<Stream<String>> streamSupplier = () -> list.stream();
IntStream.range('a', 'z').forEach(i -> {
int strlen = streamSupplier.get()
.filter(k -> {
char ch = (char) i;
return k.contains("" + ch);
}
)
.map(s -> s.length())
.mapToInt(Integer::new)
.sum();
System.out.println((char) i + " : " + strlen);
}
);
}
}
我期望的最终输出(结果)就像是 “p:17”
由于字符'p'出现在单词php,python,perl,lisp中,它将这些单词相加并返回stringlength为17。
最好是
map<String,int> with the size of 1
或其他东西,只包含最长的字符串。
这里有一些伪代码,关于我如何在'普通'java中编写它:
int previousSum = 0;
for (string ch in ('a' to 'z') ) {
int stringlengthSum = findallMatchesInListandSumStringlength(stringlist,ch);
if (stringlengthSum > previousSum) {
previousSum = stringLengthSum;
longestCharacter = ch;
}
}
System.out.println("The longest sum is: " + previousSum + " by the character: " + longestcharacter);
答案 0 :(得分:1)
我不得不稍微改变并优化您的代码。最终解决方案将是:
Map.Entry<Integer, Integer> max = IntStream.range('a', 'z').boxed().collect(Collectors.toMap(i -> i, i -> list.stream()
.filter(k -> k.contains("" + (char) i.intValue()))
.map(String::length)
.mapToInt(Integer::new)
.sum()))
.entrySet().stream()
.max((e1, e2) -> e1.getValue().compareTo(e2.getValue())).get();
System.out.println((char)max.getKey().intValue() + ":" + max.getValue());
变更是:
1)将IntStream
转换为Stream<Integer>
以便能够从中收集地图
2)收集对:符号的int值 - &gt;带有此符号的单词总和
并且至少3)找到其中包含最大元素的地图条目
答案 1 :(得分:1)
你非常接近,你基本上只是错过了流的排序。
为了使整个订单更容易,您可以创建一个专用类:
class CharacterLengthSumResult implements Comparable<CharacterLengthSumResult> {
final char c;
final int sum;
CharacterLengthSumResult(char c, int sum) {
this.c = c;
this.sum = sum;
}
@Override
public int compareTo(CharacterLengthSumResult o) {
return Integer.compare(o.sum, sum);
}
}
然后流逻辑成为:
Optional<CharacterLengthSumResult> first = IntStream.range('a', 'z').mapToObj(i -> {
String c = ((char) i) + "";
int sum = list.stream().filter(s -> s.contains(c)).mapToInt(String::length).sum();
return new CharacterLengthSumResult((char)i, sum);
}).sorted().findFirst();
if (first.isPresent()) {
System.out.println(first.get().c + " -> " + first.get().sum);
}
如果您想将整个事物作为地图,您可以使用收集器扩展已排序的内容:
...sorted().collect(Collectors.toMap(s -> s.c, s -> s.sum));