Java-8:流还是更简单的解决方案?

标签 java java-8 java-stream

我有两个模型,一个 List<ModelA>我想将其转换为 List<ModelB> . 这是我的模型:

class ModelA {

    private Long id;
    private String name;
    private Integer value;

    public ModelA(Long id, String name, Integer value) {
        this.id = id;
        this.name = name;
        this.value = value;
    }

    public Long getId() {
        return id;
    }

    public String getName() {
        return name;
    }

    public Integer getValue() {
        return value;
    }
}

class ModelB {
    private Long id;
    private Map<String, Integer> valuesByName;

    public ModelB(Long id, Map<String, Integer> valuesByName) {
        this.id = id;
        this.valuesByName = valuesByName;
    }

    public Long getId() {
        return id;
    }

    public Map<String, Integer> getValuesByName() {
        return valuesByName;
    }
}

实际解决方案:

public static List<ModelB> convert(List<ModelA> models) {
        List<ModelB> toReturn = new ArrayList<>();
        Map<Long, Map<String, Integer>> helper = new HashMap<>();
        models.forEach(modelA -> {
            helper.computeIfAbsent(modelA.getId(), value -> new HashMap<>())
                    .computeIfAbsent(modelA.getName(), value -> modelA.getValue());
        });
        helper.forEach((id, valuesByName) -> toReturn.add(new ModelB(id,valuesByName)));
        return toReturn;
    }

但我认为有一个更简单的解决方案,您是否知道如何在单个流中完成或以某种方式简化它?

编辑:我想澄清的是,我不能使用 java9,我需要先按 Id-s 然后再按名称对它们进行分组。如果在 ModelB 中我有 4 个具有相同 ID 的元素,我不想要 ModelA 的新实例。

最佳答案

我结合了这两个操作,但仍然构建中间映射,因为您需要为给定的 id group 所有 name, value 对.

models.stream()
        .collect(Collectors.groupingBy(model -> model.getId(), //ModelA::getId - Using method reference
                Collectors.toMap(model -> model.getName(), model -> model.getValue(), (map1, map2) -> map1)))
        .entrySet()
        .stream()
        .map(entry -> new ModelB(entry.getKey(), entry.getValue()))
        .collect(Collectors.toList());

编辑:

我在初始答案中错过了 (map1, map2) -> map1。需要避免为 idname(相当于您的第二个 computeIfAbsent)覆盖已经存在的 value在你的代码中) 您需要选择其中之一(或合并它们),因为默认情况下它会在找到重复键时抛出 IllegalStateException

关于Java-8:流还是更简单的解决方案?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49532138/

相关文章:

java - Android 相机禁用 takePicture 上的 stopPreview

java - 当我尝试在 Jframe 中更改 Jpanel 时导致图形

Java 不支持主要次要版本 52?尽管我没有使用 Oracle Java 1.8 的新功能,为什么会发生这种情况?

java - 为什么实现接口(interface)(使用默认方法)的顺序在 Java 8 中很重要?

filter - Java - Lambda 过滤条件,忽略添加到 map

Java 8 流 - 计算器异常

java - Java无法从服务器读取数据

Java 数组 (java.lang.NullPointerException)

java - 如何检索相似对象列表中对象内部的相似值并根据这些值创建映射

Java 8 : Stream optimization, 在同一个实例上调用同一个方法两次