【Java杂记】工具类:集合工具类 Collections&CollectionUtils

1.Collections

Collections 是为了方便使用集合而产生的工具类,Arrays 方便数组使用,Collections 是方便集合使用。

1.1 sort & binarySearch

Collections 也提供了 sort 和 binarySearch 方法,sort 底层使用的就是 Arrays.sort 方法,binarySearch 底层是自己重写了二分查找算法,实现的逻辑和 Arrays 的二分查找算法完全一致,这两个方法上 Collections 和 Arrays 的内部实现很类似,接下来我们来看下 Collections 独有的特性。

1.2 max/min

提供了 max 方法来取得集合中的最大值,min 方法来取得集合中的最小值,max 和 min 方法很相似的,这里以 max 方法为例来说明一下。max 提供了两种类型的方法,一个需要传外部排序器,一个不需要传排序器,但需要集合中的元素强制实现 Comparable 接口,后者的泛型定义很有意思,我们来看下(从右往左看):
图片描述从这段源码中,我们可以学习到两点:

  1. max 方法泛型 T 定义得非常巧妙,意思是泛型必须继承 Object 并且实现 Comparable 的接口。一般让我们来定义的话,我们可以会在方法里面去判断有无实现 Comparable 的接口,这种是在运行时才能知道结果。而这里泛型直接定义了必须实现 Comparable 接口,在编译的时候就可告诉使用者,当前类没有实现 Comparable 接口,使用起来很友好;
  2. 给我们提供了实现两种排序机制的好示例:自定义类实现 Comparable 接口和传入外部排序器。两种排序实现原理类似,但实现有所差别,我们在工作中如果需要些排序的工具类时,可以效仿。

1.3 封装了多种类型的集合

Collections 对原始集合类进行了封装,提供了更好的集合类给我们,一种是线程安全的集合,一种是不可变的集合,针对 List、Map、Set 都有提供,我们先来看下线程安全的集合:

1.线程安全的集合

线程安全的集合方法都是 synchronized 打头的,如下:
在这里插入图片描述

这些方法都是直接返回其内部类,内部类对原有api进行了加锁;从方法命名我们都可以看出来,底层是通过 synchronized 轻量锁来实现的,我们以 synchronizedList 为例来说明下底层的实现:

在这里插入图片描述

可以看到 List 的所有操作方法都被加上了 synchronized 锁,所以多线程对集合同时进行操作,是线程安全的。

2.不可变的集合

得到不可变集合的方法都是以 unmodifiable 开头的。

  • 我们会从(有数据的)原集合中,得到一个不可变的新集合,新集合只能访问,无法修改;
  • 一旦修改,就会抛出异常。这主要是因为只开放了查询方法,其余任何修改操作都会抛出异常,我们以 unmodifiableList 为例来看下底层实现机制:
    在这里插入图片描述

以上两种 List 其实解决了日常开发中一的些困惑,比如说 ArrayList 是线程不安全的,然后其内部数组很容易被修改,有的时候,我们希望 List 一旦生成后,就不能被修改,Collections 对 List 重新进行了封装,提供了两种类型的集合封装形式,从而解决了工作中的一些烦恼。这里也给了我们启示,如果平时使用 List 时有一些烦恼,也可以学习此种方式,自己对原始集合进行封装,来解决 List 使用过程中的不方便。

2.CollectionUtils

2.1 is(Not)Empty:非空判断

boolean isEmpty(Collection coll)
boolean isNotEmpty(Collection coll)
@Test
public void testIsEmpty(){

    class Person{}
    class Girl extends Person{}

    List<Integer> first = new ArrayList<>();
    List<Integer> second = null;
    List<Person> boy = new ArrayList<>();
    //每个男孩心里都装着一个女孩
    boy.add(new Girl());
    //判断集合是否为空
    System.out.println(CollectionUtils.isEmpty(first));   //true
    System.out.println(CollectionUtils.isEmpty(second));   //true
    System.out.println(CollectionUtils.isEmpty(boy));   //false

    //判断集合是否不为空
    System.out.println(CollectionUtils.isNotEmpty(first));   //false
    System.out.println(CollectionUtils.isNotEmpty(second));   //false
    System.out.println(CollectionUtils.isNotEmpty(boy));   //true
}

2.2 isEqualCollection:相等判断

boolean isEqualCollection(Collection a, Collection b)
@Test
public void testIsEmpty(){

    class Person{}
    class Girl extends Person{}

    List<Integer> first = new ArrayList<>();
    List<Integer> second = null;
    List<Person> boy = new ArrayList<>();
    //每个男孩心里都装着一个女孩
    boy.add(new Girl());
    //判断集合是否为空
    System.out.println(CollectionUtils.isEmpty(first));   //true
    System.out.println(CollectionUtils.isEmpty(second));   //true
    System.out.println(CollectionUtils.isEmpty(boy));   //false

    //判断集合是否不为空
    System.out.println(CollectionUtils.isNotEmpty(first));   //false
    System.out.println(CollectionUtils.isNotEmpty(second));   //false
    System.out.println(CollectionUtils.isNotEmpty(boy));   //true
}

2.3 union:并集

Collection union(Collection a, Collection b)
@Test
public void testUnion(){
    String[] arrayA = new String[] { "A", "B", "C", "D", "E", "F" };  
    String[] arrayB = new String[] { "B", "D", "F", "G", "H", "K" };
    List<String> listA = Arrays.asList(arrayA);
    List<String> listB = Arrays.asList(arrayB);
    //2个数组取并集 
    System.out.println(ArrayUtils.toString(CollectionUtils.union(listA, listB)));
    //[A, B, C, D, E, F, G, H, K]
}

2.4 intersection:交集

Collection intersection(Collection a, Collection b)
@Test
public void testIntersection(){
    String[] arrayA = new String[] { "A", "B", "C", "D", "E", "F" };  
    String[] arrayB = new String[] { "B", "D", "F", "G", "H", "K" };
    List<String> listA = Arrays.asList(arrayA);
    List<String> listB = Arrays.asList(arrayB);
    //2个数组取交集 
    System.out.println(ArrayUtils.toString(CollectionUtils.intersection(listA, listB)));
    //[B, D, F]
}

2.5 disjunction: 交集的补集(折取)

Collection disjunction(Collection a, Collection b)
@Test
public void testDisjunction(){
    String[] arrayA = new String[] { "A", "B", "C", "D", "E", "F" };  
    String[] arrayB = new String[] { "B", "D", "F", "G", "H", "K" };
    List<String> listA = Arrays.asList(arrayA);
    List<String> listB = Arrays.asList(arrayB);
    //2个数组取交集 的补集
    System.out.println(ArrayUtils.toString(CollectionUtils.disjunction(listA, listB)));
    //[A, C, E, G, H, K]
}

2.6 subtract:差集(扣除)

Collection subtract(Collection a, Collection b)
@Test
public void testSubtract(){
    String[] arrayA = new String[] { "A", "B", "C", "D", "E", "F" };  
    String[] arrayB = new String[] { "B", "D", "F", "G", "H", "K" };
    List<String> listA = Arrays.asList(arrayA);
    List<String> listB = Arrays.asList(arrayB);
    //arrayA扣除arrayB
    System.out.println(ArrayUtils.toString(CollectionUtils.subtract(listA, listB)));
    //[A, C, E]

}

2.7 unmodifiableCollection:生成不可改集合

Collection unmodifiableCollection(Collection collection)
@Test
// 我们对c进行操作,s也同样获得了和c相同的内容,这样就可以避免其他人员修改这个s对象。有时候需要对它进行保
// 护,避免返回结果被人修改
public void testUnmodifiableCollection(){
    Collection<String> c = new ArrayList<>();
    Collection<String> s = CollectionUtils.unmodifiableCollection(c);
    c.add("boy");
    c.add("love");
    c.add("girl");
    //! s.add("have a error");
    System.out.println(s);
}
已标记关键词 清除标记
表情包
插入表情
评论将由博主筛选后显示,对所有人可见 | 还能输入1000个字符
相关推荐
©️2020 CSDN 皮肤主题: 技术黑板 设计师:CSDN官方博客 返回首页