【Java基础】JDK内置工具类Collections类使用

collections类使用

  • Collections是JDK提供的工具类,同样位于java.util包中。它提供了一系列静态方法,能更方便地操作各种集合

1.addAll()

 boolean addAll(Collection<? super T> c, T... elements) { ... }

addAll()方法可以给一个Collection类型的集合添加若干元素。因为方法类型是Collection,所以我们可以传入List,Set等各种集合类型。

2.创建空集合

  • 创建空List:List<T> emptyList()
  • 创建空Map:Map<K, V> emptyMap()
  • 创建空Set:Set<T> emptySet()

要注意到返回的空集合是不可变集合,无法向其中添加或删除元素

此外,也可以用各个集合接口提供的of(T…)方法创建空集合。例如,以下创建空List的两个方法是等价的:

List<String> list1 = List.of();
List<String> list2 = Collections.emptyList();

3.创建单元素集合

  • 创建一个元素的List:List<T> singletonList(T o)
  • 创建一个元素的Map:Map<K, V> singletonMap(K key, V value)
  • 创建一个元素的Set:Set<T> singleton(T o)

要注意到返回的单元素集合也是不可变集合,无法向其中添加或删除元素

此外,也可以用各个集合接口提供的of(T…)方法创建单元素集合,实际上,使用List.of(T...)更方便,因为它既可以创建空集合,也可以创建单元素集合,还可以创建任意个元素的集合

List<String> list1 = List.of(); // empty list
List<String> list2 = List.of("apple"); // 1 element
List<String> list3 = List.of("apple", "pear"); // 2 elements
List<String> list4 = List.of("apple", "pear", "orange"); // 3 elements

List.of(),Set.of),Map.of()JDK9新增的方法

4.排序

Collections.sort()可以直接给List集合排序,或者使用比较器Comparable/Comparator指定条件排序

  • <T extends Comparable<? super T>> void sort(List list)
  • void sort(List list, Comparator<? super T> c)
  • void sort(Comparator<? super E> c)
    public static void main(String[] args) {
        List<String> list = new ArrayList<>();
        list.add("apple");
        list.add("pear");
        list.add("orange");
        // 排序前:
        System.out.println(list);
        Collections.sort(list);
        // 排序后:
        System.out.println(list);
    }

5.洗牌

Collections.shuffle()提供了洗牌算法,即传入一个有序的List,可以随机打乱List内部元素的顺序,即对集合进行随机排序

    public static void main(String[] args) {
        List<Integer> list = new ArrayList<>();
        for (int i=0; i<10; i++) {
            list.add(i);
        }
        // 洗牌前:
        System.out.println(list);
        Collections.shuffle(list);
        // 洗牌后:
        System.out.println(list);
    }

6.不可变集合

Collections还提供了一组方法把可变集合封装成不可变集合:

  • 封装成不可变List:List<T> unmodifiableList(List<? extends T> list)
  • 封装成不可变Set:Set<T> unmodifiableSet(Set<? extends T> set)
  • 封装成不可变Map:Map<K, V> unmodifiableMap(Map<? extends K, ? extends V> m)

这种封装实际上是通过创建一个代理对象,拦截掉所有修改方法实现的。我们来看看效果:

public static void main(String[] args) {
        List<String> mutable = new ArrayList<>();
        mutable.add("apple");
        mutable.add("pear");
        // 变为不可变集合:
        List<String> immutable = Collections.unmodifiableList(mutable);
        immutable.add("orange"); // UnsupportedOperationException!
}

然而,继续对原始的可变List进行增删是可以的,并且,会直接影响到封装后的“不可变”List:

    public static void main(String[] args) {
        List<String> mutable = new ArrayList<>();
        mutable.add("apple");
        mutable.add("pear");
        // 变为不可变集合:
        List<String> immutable = Collections.unmodifiableList(mutable);
        mutable.add("orange");
        System.out.println(immutable);
    }

因此,如果我们希望把一个可变List封装成不可变List,那么返回不可变List后,最好立刻让GC回收可变List,这样可以保证后续操作不会意外改变原始对象,从而造成“不可变”List变化了:

 public static void main(String[] args) {
        List<String> mutable = new ArrayList<>();
        mutable.add("apple");
        mutable.add("pear");
        // 变为不可变集合:
        List<String> immutable = Collections.unmodifiableList(mutable);
        // 立刻扔掉mutable的引用:
        mutable = null;
        System.out.println(immutable);
    }

7. 线程安全集合

Collections还提供了一组方法,可以把线程不安全的集合变为线程安全的集合:

  • 变为线程安全的List:List<T> synchronizedList(List<T> list)
  • 变为线程安全的Set:Set<T> synchronizedSet(Set<T> s)
  • 变为线程安全的Map:Map<K,V> synchronizedMap(Map<K,V> m)

因为从Java 5开始,引入了更高效的并发集合类,所以上述这几个同步方法已经没有什么用了

8.查询指定下标

binarySearch(Collection,Object)方法的使用(含义:查找指定集合中的元素,返回所查找元素的索引

public static void main(String[] args) {
    List c = new ArrayList();
    c.add("w");
    c.add("o");
    c.add("r");
    c.add("l");
    c.add("d");
   System.out.println("TAG", "初始集合:"+c);//[w, o, r, l, d]

    int m = Collections.binarySearch(c, "l");
  System.out.println("TAG", "找元素的索引:"+m);//-1
}

9.indexOfSubList

int indexOfSubList(List<?> source, List<?> target)查找subList在list中首次出现位置的索引

public static void main(String[] args) {
    List list = Arrays.asList("one two three four five six siven".split(" "));
   System.out.println("TAG", "初始集合:"+list);//[one, two, three, four, five, six, siven]
    List subList = Arrays.asList("three four five six".split(" "));
   System.out.println("TAG", "子集合:"+subList);//[three, four, five, six]
    System.out.println("TAG", "子集合首次出现位置的索引:"+Collections.indexOfSubList(list, subList));//2
}

10.lastIndexOfSubList

int lastIndexOfSubList(List<?> source, List<?> target)查找subList在list中最后出现位置的索引

public static void main(String[] args) {
    List list = Arrays.asList("one two three four five six siven one two three four five six siven".split(" "));
    System.out.println(("TAG", "初始集合:"+list);//[one, two, three, four, five, six, siven, one, two, three, four, five, six, siven]
    List subList = Arrays.asList("three four five six".split(" "));
    System.out.println("TAG", "子集合:"+subList);//[three, four, five, six]
   System.out.println("TAG", "子集合首次出现位置的索引:"+Collections.indexOfSubList(list, subList));//2
   System.out.println("TAG", "子集合最后出现位置的索引:"+Collections.lastIndexOfSubList(list, subList));//9
}

11.替换集合中指定元素

<T> boolean replaceAll(List<T> list, T oldVal, T newVal)替换指定元素为某元素,若要替换的值(旧元素)存在刚返回true,反之返回false

public static void main(String[] args) {
    List list = Arrays.asList("old one two three four old five six siven old".split(" "));
   System.out.println("TAG", "初始集合:"+list);//[old, one, two, three, four, old, five, six, siven, old]
    System.out.println("TAG", "替换值是否存在:"+Collections.replaceAll(list, "old", "two"));//true
    System.out.println("TAG", "替换后集合:"+list);//[new, one, two, three, four, new, five, six, siven, new]
}

12.反转List集合中元素的顺序

void reverse(List<?> list)

public static void main(String[] args) {
    List list = Arrays.asList("one two three four five six siven".split(" "));
    System.out.println("TAG", "初始集合:" + list);//[one, two, three, four, five, six, siven]
    Collections.reverse(list);
    System.out.println("TAG", "反转后集合:" + list);//[siven, six, five, four, three, two, one]
}

13.集合中的元素向后移m个位置

void rotate(List<?> list, int distance) 集合中的元素向后移m个位置,在后面被遮盖的元素循环到前面来

public static void main(String[] args) {
    List list = Arrays.asList("one two three four five six siven".split(" "));
    System.out.println("TAG", "初始集合:" + list);//[one, two, three, four, five, six, siven]
    Collections.rotate(list, 2);
    System.out.println("TAG", "旋转后集合:" + list);//[six, siven, one, two, three, four, five]
}

14.拷贝List集合

<T> void copy(List<? super T> dest, List<? extends T> src) 将集合n中的元素全部复制到m中,并且覆盖相应索引的元素((从0开始覆盖,后面的元素向后移))

public static void main(String[] args) {
     List m = Arrays.asList("one two three four five six siven".split(" "));
  System.out.println("TAG", "初始集合:" + m);//[one, two, three, four, five, six, siven]
    List n = Arrays.asList("我是 复制 过来的哈".split(" "));
   System.out.println("TAG", "待复制集合:" + n);//[我是, 复制, 过来的哈]
    Collections.copy(m, n);
    System.out.println("TAG", "复制后集合:" + m);//[我是, 复制, 过来的哈, four, five, six, siven]
}

15.交换List集合/数组中指定元素索引的位置

  • void swap(List<?> list, int i, int j)
  • void swap(Object[] arr, int i, int j)

交换集合中指定元素索引的位置

public static void main(String[] args) {
     List m = Arrays.asList("one two three four five six siven".split(" "));
    System.out.println("TAG", "初始集合:" + m);//[one, two, three, four, five, six, siven]
    Collections.swap(m, 2, 3);
    System.out.println("TAG", "交换后集合:" + m);//[one, two, four, three, five, six, siven]
}

16. 用一个元素替换List集合所有元素

** void fill(List<? super T> list, T obj) 用对象obj替换集合list中的所有元素 **

public static void main(String[] args) {
       List m = Arrays.asList("one two three four five six siven".split(" "));
    System.out.println("TAG", "初始集合:" + m);//[one, two, three, four, five, six, siven]
    Collections.fill(m, "haha12345");
    System.out.println("TAG", "替换后集合:" + m);//[haha12345, haha12345, haha12345, haha12345, haha12345, haha12345, haha12345]
}

猜你喜欢

转载自blog.csdn.net/qq877728715/article/details/104138316