【问题标题】:How to Get common Items from a stream of objects in Java8如何从 Java8 中的对象流中获取常用项
【发布时间】:2018-08-09 05:05:58
【问题描述】:

我有 2 个 Coll 对象流,我想在这里找到基于实例变量 i 的公共对象。我需要使用 Java 8 流来做到这一点。 此外,我还需要更新j 变量,比如公共元素的乘数为 1000。

class Coll
{
Integer i;
Integer j;

public Coll(Integer i, Integer j) {
    this.i = i;
    this.j = j;
}

public Integer getI() {
    return i;
}

public void setI(Integer i) {
    this.i = i;
}

public Integer getJ() {
    return j;
}

public void setJ(Integer j) {
    this.j = j;
}

}

我正在拧类似的东西:

 public static void main(String args[])
{
    Stream<Coll> stream1 = Stream.of(new Coll(1,10),new Coll(2,20),new Coll(3,30) );
    Stream<Coll> stream2 = Stream.of(new Coll(2,20),new Coll(3,30),new Coll(4,40) );

    Stream<Coll> common = stream1
            .filter(stream2
                    .map(x->x.getI())
                    .collect(Collectors.toList())
                    ::equals(stream2
                                .map(x->x.getI()))
                                .collect(Collectors.toList()));
    common.forEach( x-> x.setJ(x.getJ()*1000));
    common.forEach(x -> System.out.println(x));

}

我在 equals 方法周围做错了!我猜Java8不支持像equals这样的带参数的方法!!

我收到一个编译错误:expected a ')' or ';' around equals 方法

【问题讨论】:

  • 你的预期输出是什么?
  • 您不能在一个流上进行多个终止操作 - 所以两个 forEach 不起作用。
  • 我猜Java8不支持带参数的方法...当然支持。 Java 在向后兼容性方面非常重视。

标签: java java-8 java-stream


【解决方案1】:

你可以这样做,

Map<Integer, Coll> colsByI = listTwo.stream()
    .collect(Collectors.toMap(Coll::getI, Function.identity()));
List<Coll> commonElements = listOne.stream()
    .filter(c -> Objects.nonNull(colsByI.get(c.getI())) && c.getI().equals(colsByI.get(c.getI()).getI()))
    .map(c -> new Coll(c.getI(), c.getJ() * 1000))
    .collect(Collectors.toList());

【讨论】:

    【解决方案2】:

    移动逻辑收集外部Stream2的所有i。如果另一个列表中存在i,则过滤stream1中的所有Coll

    List<Integer> secondCollStreamI = stream2
                .map(Coll::getI)
                .collect(Collectors.toList());
    Stream<Coll> common = stream1
                .filter(coll -> secondCollStreamI.contains(coll.getI()));
    
    
    common.forEach( x-> x.setJ(x.getJ()*1000));
    common.forEach(x -> System.out.println(x));
    

    最后一条语句将导致IllegalStateException (stream has already been operated upon or closed),因为您无法重用流。您需要在某处将其收集到 List&lt;Coll&gt;... 之类的...

    List<Coll> common = stream1
                .filter(coll -> secondCollStreamI.contains(coll.getI()))
                .collect(Collectors.toList());
    
    common.forEach(x -> x.setJ(x.getJ() * 1000));
    common.forEach(System.out::println);
    

    或者,如果您想在不收集的情况下即时执行所有操作

    stream1
            .filter(coll -> secondCollStreamI.contains(coll.getI()))
            .forEach(x->  {
                x.setJ(x.getJ()*1000);
                System.out.println(x);
            });
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-08-08
      • 1970-01-01
      • 1970-01-01
      • 2016-10-26
      • 1970-01-01
      • 2018-05-04
      • 2022-11-12
      相关资源
      最近更新 更多