You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何对比两个特定结构的Map并生成关联后的新Map?

Map关联转换实现方案

核心思路

要完成从map1和map2到map3的转换,核心步骤如下:

  1. 遍历map1的每一组城市ID与子城市集合列表
  2. 提取列表中的第二个子城市集合(注意List索引从0开始,对应get(1))
  3. 遍历该子城市集合中的每个ID,到map2中查找对应的村庄ID集合
  4. 将所有关联的村庄ID合并为一个Set,作为该城市ID在map3中的值
  5. 处理边界情况:过滤列表长度不足2的城市、忽略map2中不存在的子城市ID

代码实现

方式一:Java 8+ Stream API(简洁高效)

import java.util.*;
import java.util.stream.Collectors;

public class MapConverter {
    public static Map<Long, Set<Long>> convertToCityVillageMap(Map<Long, List<Set<Long>>> citySubtierMap, Map<Long, Set<Long>> subtierVillageMap) {
        return citySubtierMap.entrySet().stream()
                // 过滤掉列表为空或长度不足2的城市
                .filter(entry -> entry.getValue() != null && entry.getValue().size() >= 2)
                .collect(Collectors.toMap(
                        Map.Entry::getKey,
                        entry -> entry.getValue().get(1).stream()
                                // 根据子城市ID获取村庄集合
                                .map(subtierVillageMap::get)
                                // 过滤map2中不存在的子城市对应的null值
                                .filter(Objects::nonNull)
                                // 将多个村庄集合展开为单个流
                                .flatMap(Set::stream)
                                // 收集为去重的村庄ID集合
                                .collect(Collectors.toSet())
                ));
    }

    // 测试示例
    public static void main(String[] args) {
        // 构建测试用map1
        Map<Long, List<Set<Long>>> map1 = new HashMap<>();
        map1.put(1L, Arrays.asList(
                new HashSet<>(Arrays.asList(10L, 11L)),
                new HashSet<>(Arrays.asList(2L, 3L))
        ));
        map1.put(2L, Arrays.asList(
                new HashSet<>(Arrays.asList(20L)),
                new HashSet<>(Arrays.asList(4L))
        ));
        // 这个城市的列表只有1个元素,会被过滤
        map1.put(3L, Collections.singletonList(new HashSet<>(Arrays.asList(30L))));

        // 构建测试用map2
        Map<Long, Set<Long>> map2 = new HashMap<>();
        map2.put(2L, new HashSet<>(Arrays.asList(201L, 202L)));
        map2.put(3L, new HashSet<>(Arrays.asList(301L)));
        map2.put(4L, new HashSet<>(Arrays.asList(401L, 402L, 403L)));

        Map<Long, Set<Long>> map3 = convertToCityVillageMap(map1, map2);
        System.out.println(map3);
        // 输出结果:{1=[201, 202, 301], 2=[401, 402, 403]}
    }
}

方式二:传统循环(直观易懂)

如果不熟悉Stream API,也可以用传统循环实现:

import java.util.*;

public class MapConverterLoop {
    public static Map<Long, Set<Long>> convertToCityVillageMap(Map<Long, List<Set<Long>>> citySubtierMap, Map<Long, Set<Long>> subtierVillageMap) {
        Map<Long, Set<Long>> cityVillageMap = new HashMap<>();

        for (Map.Entry<Long, List<Set<Long>>> entry : citySubtierMap.entrySet()) {
            Long cityId = entry.getKey();
            List<Set<Long>> subtierList = entry.getValue();

            // 跳过无效的列表
            if (subtierList == null || subtierList.size() < 2) {
                continue;
            }

            Set<Long> subtierIds = subtierList.get(1);
            Set<Long> villageIds = new HashSet<>();

            // 遍历子城市ID,合并对应的村庄ID
            for (Long subtierId : subtierIds) {
                Set<Long> villages = subtierVillageMap.get(subtierId);
                if (villages != null) {
                    villageIds.addAll(villages);
                }
            }

            // 可以选择只保留有村庄关联的城市,或者直接放入空Set
            if (!villageIds.isEmpty()) {
                cityVillageMap.put(cityId, villageIds);
            }
        }

        return cityVillageMap;
    }
}

关键注意事项

  • 索引正确性:List的索引从0开始,需求中的“第二个Set元素”对应get(1),务必确认业务逻辑中的列表顺序是否符合预期
  • 空值防护:必须检查map1的列表是否为null、长度是否足够,以及map2中是否存在子城市ID,避免抛出NullPointerException
  • 去重处理:使用HashSet存储村庄ID会自动去重,如果业务需要保留重复值(极少场景),可以替换为ArrayList并调整收集逻辑
  • 线程安全:如果在多线程环境下使用,建议替换为ConcurrentHashMap、CopyOnWriteArraySet等线程安全集合

内容的提问来源于stack exchange,提问作者Klaus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.28 19:35:11