如何使用Lambda Expression获得单词平均长度

may*_*ʎɐɯ 10 java lambda java-8 java-stream

我有一个单词列表文本文件,我想从该文件中获取最小,最大和平均单词长度.

我有一个流方法:

public static Stream<String> readWords(String filename) {
    try {
        BufferedReader reader = new BufferedReader(new FileReader(filename));
        Stream<String> stringStream = reader.lines();
        return stringStream;
    } catch (IOException exn) {
        return Stream.<String>empty();
    }
}
Run Code Online (Sandbox Code Playgroud)

在我的主要测试方法中,我打印最大和最小

System.out.println(readWords(filename)
        .min(Comparator.comparing(s -> s.length()))
        .get()
        .length()
);
System.out.println(readWords(filename)
        .max(Comparator.comparing(s -> s.length()))
        .get()
        .length()
);
Run Code Online (Sandbox Code Playgroud)

它按预期工作.

问题:
是否有可能像我在min和max中那样得到单词长度的平均值?在是或否的情况下,如何做到这一点(仅作为Lambda表达式)?

rge*_*man 13

lines()方法将为您提供线条流,而不是单词.一旦你有了Stream,调用flatMap用单词替换行,提供lambda表达式来拆分单词:

Stream<String> stringStream = reader.lines().flatMap( line -> 
    Stream.of(line.split("\\s+"))
);
Run Code Online (Sandbox Code Playgroud)

这将纠正你的maxmin.的实现.它还会影响您希望实施的任何平均计算的正确性.

要获得平均值,您可以调用mapToInt将单词流映射到它们的长度(产生一个IntStream),然后调用average,返回一个OptionalDouble.

System.out.println(readWords(filename)
    .mapToInt( s -> s.length() )  // or .mapToInt(String::length)
    .average()
    .getAsDouble());
Run Code Online (Sandbox Code Playgroud)

  • 如何`summaryStatistics()` - https://docs.oracle.com/javase/8/docs/api/java/util/stream/IntStream.html#summaryStatistics-- (3认同)
  • @ bayou.io是的,`summaryStatistics()`会起作用.它将返回一个`IntSummaryStatistics`,它给出平均值和更多:count,sum,min和max. (3认同)
  • 不要为行的单词创建临时数组.使用`flatMap(Pattern.compile("\\ s +"):: splitAsStream)`.而且您不需要手动处理`BufferedReader`.参见[`Files.lines()`](http://docs.oracle.com/javase/8/docs/api/java/nio/file/Files.html#lines-java.nio.file.Path-) (2认同)

Dav*_*rad 7

使用IntSummaryStatistics以获得最大,最小和平均一通.

IntSummaryStatistics summary = readWords(filename)
    .collect(Collectors.summarizingInt(String::length));
System.out.format("min = %d, max = %d, average = %.2f%n",
    summary.getMin(), summary.getMax(), summary.getAverage());
Run Code Online (Sandbox Code Playgroud)


Man*_*dis 6

根据有关减少的官方文件

System.out.println(readWords(filename)
                .mapToInt(String::length)
                .average()
                .getAsDouble()
);
Run Code Online (Sandbox Code Playgroud)

请注意,您可以并且可能应该使用方法引用 String::length