[在收集流时如何使用Guava的Multisets.toMultiSet()?

问题描述 投票:0回答:1

我有一个字符串列表,其中每个字符串由字母组成,这些字母由字符','(逗号)分隔。我想遍历字符串列表,以逗号分隔,计算每个字母出现多少次,并将结果存储在Multiset中。空白字符串应被忽略,并且拆分部分应修剪。多重集应按键排序。

下面的代码有效,即,它产生所需的Multiset。但是,我无法弄清楚如何使用正确的收集器方法(Multisets.toMultiset()),因此诉诸于两步解决方案,使用了一个我想消除的临时列表变量。

如果有人可以告诉我如何在收集步骤中构造对Multisets.toMultiset()的调用,我将不胜感激。我陷入了定义元素函数和供应商函数的困境,我什至无法编写已编译的代码...

@Test
public void testIt() {
    List<String> temp = Stream.of("b, c", "a", "  ", "a, c")
            .filter(StringUtils::isNotBlank)
            .map(val -> val.split(","))
            .flatMap(Arrays::stream)
            .map(String::trim)
            .collect(Collectors.toList());

    Multiset<String> multiset = ImmutableSortedMultiset.copyOf(temp);

    System.out.println("As list: " + temp);
    System.out.println("As multiset: " + multiset);
    // Output is:
    // As list: [b, c, a, a, c]
    // As multiset: [a x 2, b, c x 2]
}

我正在使用番石榴28.1。上面的示例中还使用了commons-lang3版本3.9中的StringUtils类

这是实际情况中的简化示例,但仍然可以捕捉到我的问题的本质

java java-8 guava
1个回答
0
投票

如果您真的想省略第二个复制阶段,有几种方法可以实现这一目标:

  1. 已经指定了ImmatbleSortedMultiset收集器

    .collect(ImmutableSortedMultiset.toImmutableSortedMultiset(Comparator.naturalOrder()));
    
  2. 因为您一直在问如何使用MultiSets::toMultiset来做到这一点>

    .collect(Multisets.toMultiset(Function.identity(), i -> 1, TreeMultiset::create));
    
  3. 或者您可以使用Builder]完美地添加自己的Collector实现。

    .collect(Collector.of(
        ImmutableSortedMultiset::<String>naturalOrder,
        ImmutableSortedMultiset.Builder::add,
        (b1, b2) -> {b1.addAll(b2.build()); return b1;},
        ImmutableSortedMultiset.Builder::build)
    );
    
© www.soinside.com 2019 - 2024. All rights reserved.