带你正确的使用List的retainAll方法求交集

一、 retainAll 方法

public boolean retainAll(Collection<?> c) {
        //调用自己的私有方法
        return batchRemove(c, true);
    }

二、batchRemove 方法解析

如果此 collection 由于调用而发生更改,则返回 true

//集合A比较与集合B的交集
     private boolean batchRemove(Collection<?> c, boolean complement) {
             //获得当前对象的所有元素
            final Object[] elementData = this.elementData;
            //w:标记两个集合公共元素的个数
            int r = 0, w = 0;
            //设置标志位
            boolean modified = false;
            try {
                //遍历集合A
                for (; r < size; r++)
                    //判断集合B中是否包含集合A中的当前元素
                    if (c.contains(elementData[r]) == complement)
                        //如果包含则直接保存。
                        elementData[w++] = elementData[r];
            } finally {
                // 如果 c.contains() 抛出异常
                if (r != size) {
                    //复制剩余的元素
                    System.arraycopy(elementData, r,
                                     elementData, w,
                                     size - r);
                    //w为当前集合A的length
                    w += size - r;
                }
                //如果集合A的大小放生改变
                if (w != size) {
                    // 清除工作
                    for (int i = w; i < size; i++)
                        elementData[i] = null;
                    //记录集合中元素的改变(add/remove)
                    modCount += size - w;
                    //设置当前数组的大小
                    size = w;
                    //返回为true
                    modified = true;
                }
            }
            return modified;
        }

1、关于modCount变量的说明

AbstractList包含一个modCount变量,它的初始值是0,当集合中的内容每被修改一次时(调用add(), remove()等方法),modCount加1

2、关于返回值的说明

如果集合A数组的大小没有改变,则返回false。如果集合A和集合B是完全相同的集合,也会返回false。

    public static void main(String[] args) {
        ArrayList<String> listA= new ArrayList<String>();
        listA.add("Tom");
        ArrayList<String> listB= new ArrayList<String>();
        listB.add("Tom");
        System.out.println(listA.retainAll(listB)); //false
    }

即使两个集合没有交集,也会返回true。

public static void main(String[] args) {
        ArrayList<String> listA= new ArrayList<String>();
        listA.add("Tom");
        ArrayList<String> listB= new ArrayList<String>();
        listB.add("Jack");
        System.out.println(listA.retainAll(listB));//true
    }

所以,我们要记住:当集合A的大小改变的时候返回的是True,大小没有改变的时候返回的是False。

三、正确的使用 retainAll 方法

public static void main(String[] args) {
        ArrayList<String> listA= new ArrayList<String>();
        listA.add("Tom");
        ArrayList<String> listB= new ArrayList<String>();
        listB.add("Tom");
        listA.retainAll(listB);
        if(listA.size()>0){
            System.out.println("这两个集合有相同的交集");
        }else{
            System.out.println("这两个集合没有相同的交集");
        }
    }

1、首先调用retainAll的方法

2、通过判断集合的大小,来确定是否存在交集。不能通过方法返回的True和False来判断。

时间: 2024-10-27 06:11:26

带你正确的使用List的retainAll方法求交集的相关文章

新安装ESXi 6.0 U2不能正确识别EVC模式的解决方法

新安装ESXi 6.0 U2不能正确识别EVC模式的解决方法 vSphere 6.0 U2发布了,新的版本改进了vSphere 6.0 U1b的一些错误,并且新版本支持VSAN 6.2.第一时间下载并将我的实验环境升级到 6.0 U2版本,期间发现一些问题. 我的实验环境是由4台PC机组成,每个PC机配置.连接如图1-1所示. 图1-1 实验环境 这4台PC机原来安装的是vCenter Server 6.0 u1b的版本,运行良好. 在分别将vCenter Server及ESXi升级到6.0 U

带你正确选择适合自己的韩国服务器!

如何选择适合自己的韩国服务器? 如何选择适合自己的韩国服务器? 通常选择服务器时有三种方式: 1.选择价格便宜的(如果你对产品质量没有要求,就选择这一种方式); 2.选择价格贵的(如果你是土豪,请任性地购买就OK了) 3.对产品价格和性能做一个综合评价,然后选择符合自己的. 接下来,我们开始选择过程: 这里:我们要弄清楚,不一样的价格对应的是不一样的产品品质.服务品质. 下面开始正式一起探讨选择一个性价比合适的韩服务器的过程: 一.  要选择的服务器确保是在韩国本土.如何鉴定服务器是在韩国本土呢

带你正确了解ES6

ES6全名是ECMAScript 6,是JavaScript语言的下一代标准. Babel,可以将ES6代码转为ES5代码,是一个环境执行. ES6最常用的特性:let, const, class, extends, super, arrow functions, template string, destructuring, default, rest arguments let, const类似于var,是ES6的新的声明方式. 原型.构造函数,继承看起来更清晰. 1 class Anima

【MySQL】MySQL使用正确密码却认证失败问题解决方法

前言:笔者根据 #MySQL忘记密码,重置密码方法 ,修改密码后.使用修改后的正确密码怎么也登录不上数据库,然后经过以下方法,重新登录数据库. 1.确认MySQL安装目录下没有data(Data)文件夹,如果有就删掉. 确认已经删除了data文件夹如图 2.以管理员身份打开cmd,并切换到自己磁盘中MySQL文件的bin目录下.(一般是 ...xxx\MySQL\MySQL Server 8.0\bin\ 目录) 3.初始化MySQL服务,需要在cmd窗口中输入命令:mysqld --initi

Selenium + Chrome Diver使用带用户名密码认证的HTTP代理的方法

默认情况下,Chrome的--proxy-server="http://ip:port"参数不支持设置用户名和密码认证.这样就使得"Selenium + Chrome Driver"无法使用HTTP Basic Authentication的HTTP代理.一种变通的方式就是采用IP地址认证,但在国内网络环境下,大多数用户都采用ADSL形式网络接入,IP是变化的,也无法采用IP地址绑定认证.因此迫切需要找到一种让Chrome自动实现HTTP代理用户名密码认证的方案.

Android流行界面结构——Fragment通过ViewPager(带指示器)嵌套Fragment结构的创建方法详解

原创文章,转载请注明出处http://www.cnblogs.com/baipengzhan/p/6287213.html 当前Android流行界面结构的一种--Fragment通过ViewPager嵌套Fragment结构目前非常常用,在本篇文章中, 我们一步一步将其创建出来,非常详细的让大家看到这个界面是如何实现的,下面我们开始吧. 首先我们看一下最终的效果动画,以便大家有个最初的印象. 本文章专注于功能的实现,并没有着重于界面的美观,所以大家看到的效果一般,UI效果需要大家进一步修改.

史上最全最正确的zabbix监控mysql配置方法

1.组态--主机--创建主机 2.在其他群组中选择linux server或者新建群组 3.主机名为mysql 4.模板中选择点击添加,选择Template App MySQL,点击存档 5.添加mysql监控脚本: cd /usr/local/zabbix/share/zabbix/alertscripts vi check_mysql.sh #!/bin/bash # 用户名 MYSQL_USER='zabbix' # 密码 MYSQL_PWD='123456' # 主机地址/IP MYSQ

java集合中的retainAll方法

import java.util.ArrayList; public class RetainAllDemo { public static boolean compare(int[] arr1,int[] arr2){ ArrayList<Integer> list1=new ArrayList<>(); ArrayList<Integer> list2=new ArrayList<>(); for(int a:arr1){ list1.add(a); }

在Editplus中配置java的(带包)编译(javac)和执行(java)的方法

配置的前提是电脑安装了JDK而且配置好了相关的环境变量(JAVA_HOME,path和classpath). 配置好后在命令行中输入javac和java验证是否配置成功: 假设出现上面的情况则说明配置成功. 首先打开Editplus,打开工具-配置自己定义工具(或者使用快捷键Alt+G): 然后点击"组名",将Group 1改为"Java编译与执行": 然后点击"加入工具"-"程序": 1加入编译功能 "菜单文字&q