Java8将来自2个不同对象流的数据收集到第3个对象的排序列表中

时间:2016-08-08 19:47:14

标签: java java-8 java-stream

所以这就是问题所在。我有三个课程如下:

class ObjectClassA
{
    private final long id;
    private final String name;
    private final boolean isReadOnly;
    //<some more fields>

    long getId()
    {
        return this.id;
    }

    String getName()
    {
        return this.name;
    }

    boolean isReadOnly()
    {
        return this.isReadOnly;
    }
}

class ObjectClassB
{
    private final long id;
    private final String location;
    private final boolean isReadOnly;
    //<some more fields>

    long getId()
    {
        return this.id;
    }

    String getLocation()
    {
        return this.location;
    }

    boolean isReadOnly()
    {
        return this.isReadOnly;
    }
}

class ObjectClassC
{
    private final String location;
    private final boolean isReadOnly;
    private final String location;

    String getName()
    {
        return this.name;
    }

    boolean isReadOnly()
    {
        return this.isReadOnly;
    }

    String getLocation()
    {
        return this.location;
    }
}

我有2张地图 -

Map<Id,ObjectClassA> mapObjectClassA 

Map<Id,ObjectClassB> mapObjectClassB

这两张地图的大小相同。 Id键对于两个映射都是通用的。目的是迭代任何一个地图以创建一个排序的(ObjectClassC.nameList<ObjectClassC>个对象,以便:

ObjectClassC.name = ObjectClassA.name
ObjectClassC.isReadOnly = ObjectClassA.isReadOnly || ObjectClassB.isReadOnly
ObjectClassC.location = ObjectClassB.location

这就是我现在的逻辑如下:

final List<ObjectClassC> list = 
mapObjectClassA.values()
               .stream()
               .map(a -> {
                    new ObjectClassC(a.getName(),
                                     a.isReadOnly() || mapObjectClassB.get(a.getId).isReadOnly(),
                                     mapObjectClassB.get(a.getId).getLocation())
                })
               .sorted(Comparator.comparing(ObjectClassC::getName))
               .collect(Collectors.<ObjectClassC> toList());

我的地图和集合工作正常,但我没有获得ObjectClassC个对象的排序集合。有人可以指出我出错的地方吗?

1 个答案:

答案 0 :(得分:0)

不太好,但有效。

public class MapMerge_38837365 {

    public static void main(String[] args) {
        Map<Integer, A> as = new HashMap();
        as.put(1, new A("Anna"));
        as.put(2, new A("Maria"));
        as.put(3, new A("Eva"));

        Map<Integer, B> bs = new HashMap();
        bs.put(1, new B("Adam"));
        bs.put(2, new B("Edward"));
        bs.put(3, new B("Jon"));

        Stream.concat(
                as.entrySet().stream(),
                bs.entrySet().stream()
        ).collect(Collectors.groupingBy(Map.Entry::getKey))
                .entrySet().stream()
                .map(e -> e.getValue())
                .map(e -> {
                    if (e.get(0).getValue() instanceof A)
                        return new AB((A) e.get(0).getValue(), (B) e.get(1).getValue());
                    return new AB((A) e.get(1).getValue(), (B) e.get(0).getValue());
                })
                .map(ab -> new C(ab.a.name+" " +ab.b.name))
                .forEach(System.out::println);
    }
}

&#34;高级魔法&#34;发生在Stream.concat然后groupingBy。在这两行中,我们从两个映射创建所有条目的流。然后我们按键将它们分组以映射。具有相同键(id)的元素将转到一个List<Object>。下一步是从分组映射entrySet().stream()创建新流。

然后我们提取值 - 具有相同Id&gt;的条目。 map(e -> e.getValue())

下一步是构建AB个对象,可以省略,但我想提取类型检查并转换为另一个函数。现在我们有伪对AB,这是创建Cmap(ab -> new C(ab.a.name+" " +ab.b.name))的非常好的候选者。

课程ABCAB

class A {

    final String name;

    A(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "A{" +
                "name='" + name + '\'' +
                '}';
    }
}

class B {

    final String name;

    B(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "B{" +
                "name='" + name + '\'' +
                '}';
    }
}

class C {

    final String name;

    C(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "C{" +
                "name='" + name + '\'' +
                '}';
    }
}

class AB {

    final A a;
    final B b;

    AB(A a, B b) {
        this.a = a;
        this.b = b;
    }

    @Override
    public String toString() {
        return "AB{" +
                "a=" + a +
                ", b=" + b +
                '}';
    }
}