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

如何在Java 8中移除List<Map<String,A>>中Map内对象属性的重复值

嘿,针对你这个在Java 8环境下移除List<Map<String, Object>>中HashMap内指定属性重复值的需求,我结合你提供的代码示例(咱们就以A类的age属性作为去重依据),整理了几种实用的实现方式:

先补全基础代码

首先,你的示例里用到了自定义类A,我先把它的完整定义补上(包含必要的getter/setter):

class A {
    private String age;
    private String name;

    // Getters & Setters
    public String getAge() {
        return age;
    }

    public void setAge(String age) {
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    // 可选:重写toString方便调试输出
    @Override
    public String toString() {
        return "A{age='" + age + "', name='" + name + "'}";
    }
}
基于Java 8 Stream的去重实现

咱们直接用Java 8的Stream API结合HashSet来实现去重,核心思路是用HashSet记录已经出现过的属性值,过滤掉重复项:

import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;

public class DuplicateRemovalDemo {
    public static void main(String[] args) {
        // 初始化你提供的测试数据
        List<Map<String, A>> listm = new ArrayList<>();
        
        Map<String, A> map = new HashMap<>();
        A a1 = new A();
        a1.setAge("30");
        a1.setName("Mani");
        map.put("1", a1);
        listm.add(map);

        Map<String, A> map1 = new HashMap<>();
        A a2 = new A();
        a2.setAge("31");
        a2.setName("sasi");
        map1.put("2", a2);
        listm.add(map1);

        Map<String, A> map2 = new HashMap<>();
        A a3 = new A();
        a3.setAge("31");
        a3.setName("Naveen");
        map2.put("3", a3);
        listm.add(map2);

        // 开始去重:按A类的age属性去重,保留第一个出现的元素
        Set<String> seenAges = new HashSet<>();
        List<Map<String, A>> uniqueList = listm.stream()
                .filter(mapItem -> {
                    // 从Map中取出A对象(示例中每个Map只有一个键值对,若有多个需指定键名)
                    A targetObj = mapItem.values().iterator().next();
                    String age = targetObj.getAge();
                    // HashSet.add()返回false表示值已存在,此时过滤掉当前Map
                    return seenAges.add(age);
                })
                .collect(Collectors.toList());

        // 输出验证结果
        System.out.println("去重后的集合:");
        uniqueList.forEach(System.out::println);
    }
}

运行这段代码后,输出会保留age=30和age=31的第一个Map,也就是包含Mani和sasi的两个Map,重复的Naveen对应的Map会被过滤掉。

通用化去重方法

如果后续需要切换去重的属性(比如按name去重),可以写一个通用方法,用函数式接口传递属性提取逻辑:

/**
 * 通用的List<Map>去重方法
 * @param list 待去重的集合
 * @param propertyExtractor 提取要去重的属性的函数
 * @return 去重后的集合
 */
public static <T> List<Map<String, T>> removeDuplicatesByProperty(List<Map<String, T>> list,
                                                                   java.util.function.Function<T, String> propertyExtractor) {
    Set<String> seenProperties = new HashSet<>();
    return list.stream()
            .filter(mapItem -> {
                T targetObj = mapItem.values().iterator().next();
                String propertyValue = propertyExtractor.apply(targetObj);
                return seenProperties.add(propertyValue);
            })
            .collect(Collectors.toList());
}

调用的时候就可以灵活指定属性:

// 按age去重
List<Map<String, A>> uniqueByAge = removeDuplicatesByProperty(listm, A::getAge);
// 按name去重
List<Map<String, A>> uniqueByName = removeDuplicatesByProperty(listm, A::getName);
注意事项
  • 如果你的Map中包含多个键值对,不要直接用values().iterator().next(),而是明确指定要提取的键名,比如mapItem.get("your-target-key")。
  • 上述实现默认保留第一个出现的元素,如果需要保留最后一个出现的,可以先反转原List,去重后再反转回来。
  • 确保自定义类的getter方法正确实现,否则无法正常提取属性值。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.26 11:07:05