常用List工具类(取交集、并集等等)

news2024/11/17 0:58:18

支持操作:

  • 根据指定字段,获取两个对象集合的交集、补集、并集等
  • 将对象中的多个字段值,抽取到一个List中
import java.lang.reflect.Field;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Function;
import java.util.function.Predicate;
import java.util.stream.Collectors;

/**
 * Description:List工具类。用于处理两个列表的交集、并集、差集等操作。
 *
 * @author jiangniao
 * @date 2024-3-22
 */
public class ListUtil {

    private ListUtil() {
    }

    /**
     * 提取多个字段的值到一个list
     *
     * @param list      对象集合
     * @param fieldName 需要提取的字段名
     * @return
     */
    public static List<String> extractFieldsToList(List<?> list, String... fieldName) {
        return list.stream().flatMap(item->Arrays.stream(fieldName).map(field->BeanUtils.getSimpleProperty(item, field))).collect(Collectors.toList());
    }

    /**
     * 根据指定字段找出两个列表的交集。
     *
     * @param list1
     * @param list2
     * @param fields
     * @param <T>
     * @return
     */
    public static <T> List<T> intersection(List<T> list1, List<T> list2, String... fields) {
        return list1.stream().filter(item1->containsWithFields(list2, item1, fields)).collect(Collectors.toList());
    }

    /**
     * 根据指定字段找出两个列表的并集
     *
     * @param list1
     * @param list2
     * @param fields
     * @param <T>
     * @return
     */
    public static <T> List<T> union(List<T> list1, List<T> list2, String... fields) {
        List<T> union = new ArrayList<>(list1);
        union.addAll(list2.stream().filter(item->!containsWithFields(list1, item, fields)).collect(Collectors.toList()));
        return union;
    }

    /**
     * 根据指定字段找出两个列表的差集。list1中有,list2中没有的元素
     *
     * @param list1
     * @param list2
     * @param fields
     * @param <T>
     * @return 返回list1过滤后的数据
     */
    public static <T> List<T> difference(List<T> list1, List<T> list2, String... fields) {
        return list1.stream().filter(item->!containsWithFields(list2, item, fields)).collect(Collectors.toList());
    }

    /**
     * 找出两个列表的差集。list1中有,list2中没有的元素。
     * <p>用于非Object对象的比较,比如String、Integer等
     *
     * @param list1
     * @param list2
     * @param <T>
     * @return 返回list1过滤后的数据
     */
    public static <T> List<T> difference(List<T> list1, List<T> list2) {
        list1.removeAll(list2);
        return list1;
    }

    /**
     * 辅助方法,判断列表中是否包含指定对象
     *
     * @param list
     * @param item
     * @param fields
     * @param <T>
     * @return
     */
    private static <T> boolean containsWithFields(List<T> list, T item, String... fields) {
        return list.stream().anyMatch(item2->matchesFields(item, item2, fields));
    }

    /**
     * 辅助方法,判断两个对象的指定字段是否相等
     *
     * @param item1
     * @param item2
     * @param fields
     * @param <T>
     * @return
     */
    private static <T> boolean matchesFields(T item1, T item2, String... fields) {
        try {
            for (String field : fields) {
                Field declaredField1 = item1.getClass().getDeclaredField(field);
                Field declaredField2 = item2.getClass().getDeclaredField(field);
                declaredField1.setAccessible(true);
                declaredField2.setAccessible(true);
                if (!Objects.equals(declaredField1.get(item1), declaredField2.get(item2))) {
                    return false;
                }
            }
            return true;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 根据指定字段对列表进行去重
     *
     * @param list
     * @param fields
     * @param <T>
     * @return
     */
    public static <T> List<T> distinctByFields(List<T> list, String... fields) {
        return list.stream().filter(distinctByKey(t->getKey(t, fields))).collect(Collectors.toList());
    }

    /**
     * 辅助方法,用于生成去重的键
     *
     * @param keyExtractor
     * @param <T>
     * @return
     */
    private static <T> Predicate<T> distinctByKey(Function<? super T, ?> keyExtractor) {
        Map<Object, Boolean> seen = new ConcurrentHashMap<>();
        return t->seen.putIfAbsent(keyExtractor.apply(t), Boolean.TRUE) == null;
    }

    /**
     * 辅助方法,生成由指定字段的值组成的键
     *
     * @param item
     * @param fields
     * @param <T>
     * @return
     */
    private static <T> String getKey(T item, String... fields) {
        StringBuilder key = new StringBuilder();
        try {
            for (String field : fields) {
                Field declaredField = item.getClass().getDeclaredField(field);
                declaredField.setAccessible(true);
                key.append(declaredField.get(item)).append("-");
            }
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
        return key.toString();
    }

}


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2241847.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

A029-基于Spring Boot的物流管理系统的设计与实现

&#x1f64a;作者简介&#xff1a;在校研究生&#xff0c;拥有计算机专业的研究生开发团队&#xff0c;分享技术代码帮助学生学习&#xff0c;独立完成自己的网站项目。 代码可以查看文章末尾⬇️联系方式获取&#xff0c;记得注明来意哦~&#x1f339; 赠送计算机毕业设计600…

Spring系统框架

Spring Framework系统架构 1.Spring核心概念 代码书写现状 耦合度偏高 解决方案 使用对象时&#xff0c;在程序中不要主动使用new产生对象&#xff0c;转换为外部提供对象 IOC(Inversion of Control)控制反转 对象的创建控制权由程序移到外部&#xff0c;这种思想称为控制…

鸿蒙实战:页面跳转

文章目录 1. 实战概述2. 实现步骤2.1 创建项目2.2 准备图片素材2.3 编写首页代码2.4 创建第二个页面 3. 测试效果4. 实战总结 1. 实战概述 实战概述&#xff1a;本实战通过ArkUI框架&#xff0c;在鸿蒙系统上开发了一个简单的两页面应用。首页显示问候语和“下一页”按钮&…

文献解读-DNAscope: High accuracy small variant calling using machine learning

关键词&#xff1a;基准与方法研究&#xff1b;基因测序&#xff1b;变异检测&#xff1b; 文献简介 标题&#xff08;英文&#xff09;&#xff1a;DNAscope: High accuracy small variant calling using machine learning标题&#xff08;中文&#xff09;&#xff1a;DNAsc…

程序设计方法与实践-变治法

变换之美 变治法就是基于变换的思路&#xff0c;进而使原问题的求解变得简单的一种技术。 变治法一般有三种类型&#xff1a; 实例化简&#xff1a;将问题变换为同问题&#xff0c;但换成更为简单、更易求解的实例。改变表现&#xff1a;变化为同实例的不同形式&#xff0c;…

解决Anaconda出现CondaHTTPError: HTTP 000 CONNECTION FAILED for url

解决Anaconda出现CondaHTTPError: HTTP 000 CONNECTION FAILED for url 第一类情况 在anaconda创建新环境时&#xff0c;使用如下代码 conda create -n charts python3.7 错误原因&#xff1a; 默认镜像源访问速度过慢&#xff0c;会导致超时从而导致更新和下载失败。 解决方…

Spring Boot框架:电商系统的技术革新

4 系统设计 网上商城系统的设计方案比如功能框架的设计&#xff0c;比如数据库的设计的好坏也就决定了该系统在开发层面是否高效&#xff0c;以及在系统维护层面是否容易维护和升级&#xff0c;因为在系统实现阶段是需要考虑用户的所有需求&#xff0c;要是在设计阶段没有经过全…

wordpress下载站主题推荐riproV5 wordpress日主题

iPro主题全新V5版本&#xff0c;是一个优秀且功能强大、易于管理、现代化的WordPress虚拟资源商城主题。支持首页模块化布局和WP原生小工具模块化首页可拖拽设置&#xff0c;让您的网站设计体验更加舒适。同时支持了高级筛选、自带会员生态系统、超全支付接口等众多功能&#x…

微服务即时通讯系统的实现(客户端)----(1)

目录 1. 项目整体介绍1.1 项目概况1.2 界面预览和功能介绍1.3 技术重点和服务器架构 2. 项目环境搭建2.1 安装Qt62.3 安装vcpkg2.3 安装protobuf2.4 构建项目2.5 配置CMake属性 3. 项目核心数据结构的实现3.1 创建data.h存放核心的类3.2 工具函数的实现3.3 创建编译开关 4. 界面…

2024年11月15日

1.计算机网络 逻辑右移 做加减法 定点乘法 原码乘法运算 一位乘 计组 2.英语六级

算法定制LiteAIServer摄像机实时接入分析平台玩手机打电话检测算法:智能监控的新篇章

在现代社会&#xff0c;随着智能手机的普及&#xff0c;无论是在工作场所还是公共场所&#xff0c;玩手机或打电话的行为日益普遍。然而&#xff0c;在某些特定环境下&#xff0c;如工厂生产线、仓库、学校课堂等&#xff0c;这些行为可能会影响到工作效率、安全或教学秩序。为…

算法--解决二叉树遍历问题

第一 实现树的结构 class Node(): # 构造函数&#xff0c;初始化节点对象&#xff0c;包含数据和左右子节点 def __init__(self, dataNone): self.data data # 节点存储的数据 self.left None # 左子节点&#xff0c;默认为None self.rig…

深度学习基础—Beam search集束搜索

引言 深度学习基础—Seq2Seq模型https://blog.csdn.net/sniper_fandc/article/details/143781223?fromshareblogdetail&sharetypeblogdetail&sharerId143781223&sharereferPC&sharesourcesniper_fandc&sharefromfrom_link 上篇博客讲到&#xff0c;贪心算…

C++__day1

1、思维导图 2、如果登录失败&#xff0c;提示用户登录失败信息&#xff0c;并且提示错误几次&#xff0c;且重新输入&#xff1b;如果输入错误三次&#xff0c;则退出系统 #include <iostream> using namespace std;int main() {string id , pswd;string user"admi…

【机器学习】数学知识:欧式距离(Euclidean Distance)和曼哈顿距离(Manhattan Distance)

欧式距离和曼哈顿距离是两种常用的距离度量方法&#xff0c;用于衡量两点之间的相似性或差异性。它们在几何分析、数据挖掘、机器学习等领域有广泛应用。 1. 欧式距离 概念 欧式距离&#xff08;Euclidean Distance&#xff09;是最常见的直线距离度量方法&#xff0c;源于欧…

Java之JDBC,Maven,MYBatis

前言 就是用来操作数据库的 1.JDBC快速入门 注意在使用前一定要导入jar包 在模块那里新建目录&#xff0c;新建lib&#xff0c;粘贴复制jar包&#xff0c;我这个jar设置的是模块有效 package test1017;import java.sql.Connection; import java.sql.DriverManager; import…

JavaWeb笔记整理——Spring Task、WebSocket

目录 SpringTask ​cron表达式 WebSocket SpringTask cron表达式 WebSocket

【大数据学习 | HBASE高级】rowkey的设计,hbase的预分区和压缩

1. rowkey的设计 ​ RowKey可以是任意字符串&#xff0c;最大长度64KB&#xff0c;实际应用中一般为10~100bytes&#xff0c;字典顺序排序&#xff0c;rowkey的设计至关重要&#xff0c;会影响region分布&#xff0c;如果rowkey设计不合理还会出现region写热点等一系列问题。 …

如何实现主备租户的无缝切换 | OceanBase应用实践

对于DBA而言&#xff0c;确保数据库的高可用性、容灾等能力是其日常工作中需要持续思考和关注的重要事项。一方面&#xff0c;可以利用数据库自身所具备的功能来实现这些目标&#xff1b;若数据库本身不提供相应功能&#xff0c;DBA则需寻找其他工具来增强数据库的高可用性和容…

Spring 中的 BeanDefinitionParserDelegate 和 NamespaceHandler

一、BeanDefinitionParserDelegate Spring在解析xml文件的时候&#xff0c;在遇到<bean>标签的时候&#xff0c;我们会使用BeanDefinitionParserDelegate对象类解析<bean>标签的内容&#xff0c;包括<bean>标签的多个属性&#xff0c;例如 id name class in…