如何简化嵌套HashMap,提取各设备距离最小的网关记录
解决方案
核心思路
先为每个设备筛选出距离最小的网关记录,再将这些记录重新按网关分组,即可得到期望的输出结果。
推荐的数据结构及实现代码
1. 临时存储设备最小距离记录
使用Map<String, Map.Entry<String, Double>>,key为设备ID,value存储对应的最小距离网关ID和距离(用AbstractMap.SimpleEntry封装);如果追求语义清晰,也可以自定义POJO类替代Entry。
2. 最终分组存储
用和原结构一致的Map<String, Map<String, Double>>,按网关ID分组存储属于它的最小距离设备记录,方便按期望格式输出。
完整实现代码:
import java.util.AbstractMap; import java.util.HashMap; import java.util.Map; public class GatewayDeviceDistanceProcessor { public static void main(String[] args) { // 模拟原数据 Map<String, Map<String, Double>> averageDistances = new HashMap<>(); Map<String, Double> gateway1Devices = new HashMap<>(); gateway1Devices.put("AC233FAC9623", 7.1); gateway1Devices.put("AC233FAC9624", 4.3); averageDistances.put("AC233FC0FA9F", gateway1Devices); Map<String, Double> gateway2Devices = new HashMap<>(); gateway2Devices.put("AC233FAC9623", 11.850000000000001); gateway2Devices.put("AC233FAC9624", 0.8); averageDistances.put("AC233FC0FAAE", gateway2Devices); // 第一步:收集每个设备的最小距离网关记录 Map<String, Map.Entry<String, Double>> deviceMinMap = new HashMap<>(); for (Map.Entry<String, Map<String, Double>> gatewayEntry : averageDistances.entrySet()) { String gatewayId = gatewayEntry.getKey(); Map<String, Double> deviceDists = gatewayEntry.getValue(); for (Map.Entry<String, Double> deviceEntry : deviceDists.entrySet()) { String deviceId = deviceEntry.getKey(); double dist = deviceEntry.getValue(); Map.Entry<String, Double> existing = deviceMinMap.get(deviceId); if (existing == null || dist < existing.getValue()) { deviceMinMap.put(deviceId, new AbstractMap.SimpleEntry<>(gatewayId, dist)); } } } // 第二步:按网关重新分组 Map<String, Map<String, Double>> gatewayMinDevices = new HashMap<>(); for (Map.Entry<String, Map.Entry<String, Double>> deviceEntry : deviceMinMap.entrySet()) { String deviceId = deviceEntry.getKey(); String gatewayId = deviceEntry.getValue().getKey(); double minDist = deviceEntry.getValue().getValue(); gatewayMinDevices.computeIfAbsent(gatewayId, k -> new HashMap<>()) .put(deviceId, minDist); } // 输出结果 for (Map.Entry<String, Map<String, Double>> entry : gatewayMinDevices.entrySet()) { System.out.println("Gateway: " + entry.getKey()); Map<String, Double> devices = entry.getValue(); for (Map.Entry<String, Double> deviceEntry : devices.entrySet()) { System.out.printf("Device: %s, Average Distance: %.1f%n", deviceEntry.getKey(), deviceEntry.getValue()); } System.out.println(); } } }
自定义POJO优化方案
如果觉得用Entry语义不够清晰,可以自定义一个类来存储设备的最小距离信息:
class DeviceMinDistance { private String gatewayId; private String deviceId; private double distance; public DeviceMinDistance(String gatewayId, String deviceId, double distance) { this.gatewayId = gatewayId; this.deviceId = deviceId; this.distance = distance; } // getter方法 public String getGatewayId() { return gatewayId; } public String getDeviceId() { return deviceId; } public double getDistance() { return distance; } }
此时第一步的Map改为Map<String, DeviceMinDistance>,代码可读性会更好,后续维护更方便。
输出结果
运行上述代码后,会得到期望的输出:
Gateway: AC233FC0FA9F Device: AC233FAC9623, Average Distance: 7.1 Gateway: AC233FC0FAAE Device: AC233FAC9624, Average Distance: 0.8
内容的提问来源于stack exchange,提问作者user565
相关产品推荐
相关产品推荐

