List中的并集、交集、差集的使用(并阅读源码)
总结
- 交集:两个list集合共同元素部分,retainAll()方法。
- 差集:从A集合中获取B集合中,没有的元素。removeAll()方法。
- 并集:将两个list集合并在一起,addAll()方法,但有可能出现重复元素,可以先removeAll(),去掉重复元素部分,再addAll()方法。
代码演示:
交集:retainAll()方法
package com.example.demo.list;import lombok.*;import java.util.ArrayList; import java.util.List;public class demo {public static void main(String[] args) {List<Person> list = new ArrayList<>();list.add(new Person("小明","18"));list.add(new Person("中明","28"));list.add(new Person("大明","38"));list.add(new Person("老明","48"));List<Person> list2 = new ArrayList<>();list2.add(new Person("小明","18"));list2.add(new Person("老明","48"));list2.add(new Person("老大明","58"));list2.add(new Person("老老明","68"));// 交集:共同元素部分list.retainAll(list2);System.out.println(list);}@Data@NoArgsConstructor@AllArgsConstructorstatic class Person{private String name;private String age;} }
差集:removeAll()方法
package com.example.demo.list;import lombok.*;import java.util.ArrayList; import java.util.List;public class demo {public static void main(String[] args) {List<Person> list = new ArrayList<>();list.add(new Person("小明","18"));list.add(new Person("中明","28"));list.add(new Person("大明","38"));list.add(new Person("老明","48"));List<Person> list2 = new ArrayList<>();list2.add(new Person("小明","18"));list2.add(new Person("老明","48"));list2.add(new Person("老大明","58"));list2.add(new Person("老老明","68"));// 差集:从A集合中获取B集合中,没有的元素list.removeAll(list2);System.out.println(list);}@Data@NoArgsConstructor@AllArgsConstructorstatic class Person{private String name;private String age;} }
并集:removeAll(),去掉重复元素部分,再addAll()方法。
package com.example.demo.list;import lombok.*;import java.util.ArrayList; import java.util.List;public class demo {public static void main(String[] args) {List<Person> list = new ArrayList<>();list.add(new Person("小明","18"));list.add(new Person("中明","28"));list.add(new Person("大明","38"));list.add(new Person("老明","48"));List<Person> list2 = new ArrayList<>();list2.add(new Person("小明","18"));list2.add(new Person("老明","48"));list2.add(new Person("老大明","58"));list2.add(new Person("老老明","68"));// 并集list.removeAll(list2);System.out.println("先获取list集合中不存在list2集合的元素:");System.out.println(list);list.addAll(list2);System.out.println("再将list2集合直接加到list集合中,达到去重的并集");System.out.println(list);}@Data@NoArgsConstructor@AllArgsConstructorstatic class Person{private String name;private String age;} }
源码原理
交集(retainAll())
public boolean retainAll(Collection<?> c) {// 先判断是否为nullObjects.requireNonNull(c);// 调用批量移动方法return batchRemove(c, true);}
差集(removeAll())
public boolean removeAll(Collection<?> c) {Objects.requireNonNull(c);return batchRemove(c, false);}
通过查看上面两个源码,发现都是调用了同一个batchRemove方法,只是最后传递的boolean不一样。
batchRemove()方法:
private boolean batchRemove(Collection<?> c, boolean complement) {// 设现是 集合ListA.retainAll(ListB) 则complement为true// 先把ListA的元素赋给elementData变量final Object[] elementData = this.elementData;int r = 0, w = 0;boolean modified = false;try {// 核心部分 size 是 ListA集合元素的个数for (; r < size; r++)// 通过对 ListA的元素进行遍历// 判断ListA的元素是否在ListB元素中,得到的结果再跟comlement进行比较// 上述已设调用方法:集合ListA.retainAll(ListB) 则complement为true// 则 如果ListB元素包含ListA元素的话,则会返回true == complement,走到分支if (c.contains(elementData[r]) == complement)// 这是典型的在原数组上进行操作的手法,减少内存开销,具体看下文的图片elementData[w++] = elementData[r];} finally {// Preserve behavioral compatibility with AbstractCollection,// even if c.contains() throws.if (r != size) {System.arraycopy(elementData, r,elementData, w,size - r);w += size - r;}if (w != size) {// clear to let GC do its work// 将其他赋予null 为了更好的GCfor (int i = w; i < size; i++)elementData[i] = null;modCount += size - w;size = w;modified = true;}}return modified;}
addAll()方法:
public boolean addAll(int index, Collection<? extends E> c) {rangeCheckForAdd(index);int cSize = c.size();if (cSize==0)return false;checkForComodification();// 核心parent.addAll(parentOffset + index, c);this.modCount = parent.modCount;this.size += cSize;return true;}
public boolean addAll(int index, Collection<? extends E> c) {rangeCheckForAdd(index);boolean modified = false;// 就是很普通的遍历,一个个addfor (E e : c) {add(index++, e);modified = true;}return modified;}
List中的并集、交集、差集的使用(并阅读源码)相关推荐
- Oracle中关于并集/交集/差集的运算
1.并集的运算 select name from test1 union [all] select name from test2; 使用union时,默认将对结果进行排序,union all则不进行 ...
- 交集函数oracle,Oracle中关于并集/交集/差集的运算
1.并集的运算 select name from test1 union [all] select name from test2; 使用union时,默认将对结果进行排序,union all则不 1 ...
- 高级JAVA - 利用函数式接口实现通用的取并集/交集/差集进阶版
在前文(高级JAVA - 利用函数式接口实现通用的取并集/交集/差集)中我们实现了利用函数式接口获取交集/差集 , 但是只能全部生成 , 假如我们只需要一个交集的话 , 所有代码仍然会执行一次 . 比 ...
- 高级JAVA - 利用函数式接口实现通用的取并集/交集/差集
package com.xing.dto;import com.xing.common.utils.XDataUtil; import lombok.Data;import java.util.Arr ...
- shell 文件处理 并集 交集 差集
shell 文件处理 并集 交集 差集(1个是另一个的子集时候才能用) 1. 取出两个文件的并集(重复的行只保留一份) cat file1 file2 | sort | uniq 2. 取出两个文件 ...
- 使用Set求两个数组的并集|| 交集||差集
这里要讲解一下,使用Set求两个数组的并集|| 交集||差集. 先定义两个数组: let a = new Set([1, 2, 3]);let b = new Set([4, 3, 2]); 并集 l ...
- Web 开发中很实用的10个效果【附源码下载】
在工作中,我们可能会用到各种交互效果.而这些效果在平常翻看文章的时候碰到很多,但是一时半会又想不起来在哪,所以养成知识整理的习惯是很有必要的.这篇文章给大家推荐10个在 Web 开发中很有用的效果,记 ...
- JDK源码解析 迭代器模式在JAVA的很多集合类中被广泛应用,接下来看看JAVA源码中是如何使用迭代器模式的。
JDK源码解析 迭代器模式在JAVA的很多集合类中被广泛应用,接下来看看JAVA源码中是如何使用迭代器模式的. 看完这段代码是不是很熟悉,与我们上面代码基本类似.单列集合都使用到了迭代器,我们以Arr ...
- JavaScript实现返回数字的二进制表示中使用的位数bitLength算法(附完整源码)
JavaScript实现返回数字的二进制表示中使用的位数bitLength算法(附完整源码) bitLength.js完整源代码 bitLength.js完整源代码 export default fu ...
最新文章
- JavaScript调用Applet的函数
- mysql 存储过程乱码的问题
- 达摩java_JAVA面向对象
- Note change in webclient ui - delete case research
- 20130328java基础学习笔记-循环结构for以及for,while循环区别
- mysql两张主表person event加上第三张关联表
- 7系统软raid_使用图形界面来配置RAID
- 作者:孟凡(1989-),男,中国科学院大学经济与管理学院、中国科学院大数据挖掘与知识管理重点实验室博士生...
- BAT老程序员分享:Linux C/C++ 开发程序员的黄金方向和学习路线!
- MySQL错误:The user specified as a definer (XXX@XXX) does not exist (1449错误)最简解决方案...
- python正则_正则化方法及Python实现
- 搜索引擎广告计费系统如何防恶意点击
- Python collections系列
- matlab-罗曼诺夫斯基准则剔除粗大值
- 新建文本html,创建邮件模板时html内容和文本内容哪种好
- 汽车HUD抬头显示全产业链深度解析报告
- 14届数独-真题标准数独-Day 6-20220121(补)
- Npoi 导出word控制表格水平居中
- android 休眠流程
- fiddler抓包时候的 tunnel to是什么意思
热门文章
- 复工证明怎么写 企业复工证明模板
- 清远市技术学院大学城网
- 电费管理系统-UML建模课程设计
- 医疗教学展示培训报告说明ppt模板 毕业答辩PPT 科研成果展示PPT图形素材打包
- Wincc7.5经典版 与PLC通讯
- 课程6 :PLC常见指令详解:MOVE指令,教你将数据传递至PLC界任意角落
- 内核错误:BTF: .tmp_vmlinux.btf: pahole (pahole) is not available
- 世界上最复杂的函数_世界上最轻松的工作
- RestTemplate封装方法
- IDEA中设置热部署