0
点赞
收藏
分享

微信扫一扫

[java]集合类详细总结

绣文字 2022-04-05 阅读 85
java


文章目录

一、 集合类介绍

1.1 为什么出现集合类

1.2 数组和集合的区别

  • 数组和集合类都是容器。
  • 数组声明了它容纳的元素的类型,而集合不声明。
  • 数组长度是固定的;集合长度是可变的。
  • **数组中可以存储基本数据类型和引用数据类型,集合只能存储对象。 **
  • 数组中存储数据类型是单一的,集合中可以存储任意类型的对象。
  • 数组是java语言中内置的数据类型,是线性排列的,执行效率或者类型检查都是最快的。

1.3 集合类图

  • Collection:所有集合类的根接口

  • Map:映射接口,存放键值对

  • Iterator:遍历集合的迭代接口

在这里插入图片描述在这里插入图片描述

二、 Collection接口与Iterator接口

2.1 Collection接口

  • Collection接口位置 java.util.Collection
  • Collection接口有三个子接口。Collection 接口是 List、Set 和 Queue 接口的父接口,通常情况下不被直接使用。
  • List(列表) ,Set(集)、Queue(队列)

2.1.1 Collection接口的常用方法

方法 说明
boolean add(Object o) 向集合中加入指定对象o,增加成功返回true,失败false
boolean addAll(Collection c) 将指定集合c内的所有元素添加到该集合内,增加成功返回true,否则返回false
void clear() 删除集合内的所有元素
boolean contains(Object o) 判定集合内是否包含指定元素,是返回true
boolean containsAll(Collection c) 判定集合内是否包含集合c的所有元素 ,是返回true
boolean isEmpty() 判定是否为空集合,是返回true
Iterator iterator() 返回一个Iterator对象,可以用来遍历集合中的元素
boolean remove(Object o) 从集合中删除指定元素 o,成功则返回true
boolean removeAll(Collection c) 删除该集合中包含集合c的所有元素,若删除了1个及以上的元素则返回true
boolean retainAll(Collection c) 删除该集合中除集合c中元素以外的元素,若调用该方法的集合元素改变了,则返回true
int size() 返回集合中元素的数目
Object[] toArray() 返回一个数组,该数组中包括集合中的所有元素

2.2 Iterator接口

2.2.1 Iterator接口的作用

2.2.2 Iterator接口的常用方法

方法 接口类型 说明
boolean hasNext() Iterator 还有元素可以迭代返回true
Object next() Iterator 返回下一个元素
void remove() Iterator 删除当前元素
void add(Object o) ListIterator 将指定元素o插入集合,该元素在下一次调用next()方法时被返回
boolean hasNext() ListIterator 存在下一个元素时返回true
boolean hasPrevious() ListIterator 存在前一个元素时返回true
Object next() ListIterator 返回列表中的下一个元素
Object previous() ListIterator 返回列表中的前一个元素
int nextIndex() ListIterator 返回列表下一个元素的下标,如果不存在下一个元素,则返回列表的大小
int previousIndex() ListIterator 返回列表前一个元素的下标,如果不存在前一个元素,则返回 -1
void remove() ListIterator 删除当前元素
void set(Object o) ListIterator 将o赋值给当前元素,即上一次调用next方法或previous方法后返回的元素

三、 List 集合

3.1 List 接口的特点

  • List集合为单列集合
  • 元素有序(按照元素的插入顺序保存元素),元素可重复
  • 有索引,可通过索引对元素进行操作。

3.1.1 List 实现类的特点

  • ArrayList
    • 底层数据结构是数组,查询快,增删慢。
    • 线程不安全,效率高
    • 初始容量为10,扩容1.5倍
  • LinkedList
    • 底层数据结构是链表,查询慢,增删快。
    • 线程不安全,效率高。
  • Vector
    • 底层数据结构是数组。
    • 线程安全,效率低,现已经被ArrayList替代
    • 初始容量为10,扩容2倍
  • Stack 栈
    • 底层调用Vector类中的方法,数组实现。
    • 先进后出。

3.2 List 接口的常用方法

方法 说明
boolean add(int index, Object element) index为对象element要加入的位置,其他对象的索引位置相对后移1位,索引位置从0开始
E remove(int index) 移出列表中指定位置元素
E set(int index, E element) 用指定元素替换列表中指定位置元素
E get(int index) 返回列表中指定位置元素
int indexOf(Object o) 返回列表中指定元素位置的索引。存在多个时,返回第一个的索引位置,不存在返回-1
int lastIndexOf(Object o) 返回列表中指定元素位置的索引。存在多个时,返回最后一个的索引位置,不存在返回-1
ListIterator<> listIterator() 返回此列表元素的列表迭代器(按适当顺序)
ListIterator<> listIterator(int index) 返回此列表元素的列表迭代器(按适当顺序),从列表的指定位置开始
List <> subList(int fromIndex, int toIndex) 返回一个指定区域的List集合对象,指定区域从索引fromIndex(包括)到索引toIndex(不包括)
// 利用ArrayList类实例化List集合
List<String> list = new ArrayList<>();
// 利用LinkedList类实例化List集合
List<String> lsit2 = new LinkedList<>();

3.3 ArrayList

3.3.1 ArrayList 常用方法

  • 增:add(o) add(index,o)
  • 删:remove(o) remove(index)
  • 改:set(index,o)
  • 查:
    • 单查:get(index)

    • 查所有:循环遍历
      1.for循环

         for(int i=0;i<list.size();i++){
             get(i);
         }
      

      2.迭代器

         Iterator it = list.iterator();
         while(it.hasNext()){
             Integer a = (Integer)it.next();
         }
      

      3.for增强循环

         for(Integer i:list){
             i
         }	
      

3.4 LinkedList

3.4.1 LinkedList 类的常用方法

方法 说明
void addFirst(E e) 将指定元素插入此列表的开头
void addLast(E e) 将指定元素插入此列表的结尾
E getFirst() 返回列表开头的元素
E getLast() 返回列表结尾的元素
E removeFirst() 移除列表开头的元素
E removeLast() 移除列表结尾的元素

3. Stack 栈

  1. new Stack() 初始化
  2. push(o) 添加元素
  3. pop() 移出栈定元素
  4. peek() 查栈顶元素

四、 Set 集合

4.1 Set 接口的特点

  • 单列集合
  • 无序元素不能重复
  • 无索引

4.1.1 Set 实现类的特点

  • HashSet
    • 底层数据结构是哈希表,存取速度快
    • 线程不安全
    • 元素无序,可以为null
  • LinkedHashSet(HashSet的子类)
    • 哈希表和链表实现了Set接口
    • 元素有序(按照元素的插入顺序保存元素)
  • TreeSet
    • 底层数据结构是红黑树,默认整形排序为从小到大
    • 存储的对象此项实现Comparable接口
    • 线程不安全
    • 元素可以为null

4.2 HashSet

4.2.1 HashSet 特点

  • HashSet:无序不重复,无索引
  • 默认不重复的是虚地址,要想内容不重复,就重写hashcode和equals方法。
  • 底层是HashMap实现,HashMap底层是由数组+链表+红黑树实现
  • HashSet堪称查询速度最快的集合,因为其内部是以HashCode来实现的。它内部元素的顺序是由哈希码来决定的,所以它不保证set的迭代顺序;特别是它不保证该顺序恒久不变
  • 无索引,无法使用for循环来遍历,可以使用增强for循环和迭代器来循环
  • 造成存泄露的原因:HashSet的remove方法也依赖于哈希值进行待删除节点定位,如果由于集合元素内容被修改而导致hashCode方法的返回值发生变更,那么,remove方法就无法定位到原来的对象,导致删除不成功,从而导致内存泄露。

4.2.2 判断重复的方法:

4.2.3 HashSet 常用方法

  • 增:add(o)

  • 删:remove(o) 删除指定元素 clear() 移除集合中所有的元素

  • 改:先删除,再添加

  • 查:
    1.for增强循环

     for(Integer i:set){
         i
     }
    

    2.迭代器

       Iterator it=set.iterator();
       while(it.hasNext()){
           Integer a=(Integer)it.next();
       }
    

4.3 TreeSet

4.3.1 TreeSet 特点

4.3.2 排序比较的方法

1.自然排序
    public static void main(String[] args) {
    TreeSet<String> set = new TreeSet<>();
    //增
    set.add("b");
    set.add("a");
    set.add("c");
    set.add("aa");
    set.add("cc");
    set.add("bb");
    //输出
    System.out.println(set);//按照元素的自然排序输出
}
2.自定义类
    1.内部比较器
    1.类实现Comparable接口,重写compareTo()方法
    public class Person implements Comparable<Person> {
        private String name;
        private int age;

        @Override
        public String toString() {
            return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
        }

        public Person(String name, int age) {
            this.name = name;
            this.age = age;
        }

        public Person() {
        }

        public String getName() {
            return name;
        }

        public void setName(String name) {
            this.name = name;
        }

        public int getAge() {
            return age;
        }

        public void setAge(int age) {
            this.age = age;
        }

        @Override
        public int compareTo(Person o) {
            //比较规则:1.name 2:age
            //1.name
            int i = this.name.compareTo(o.name);
            return i==0?this.age-o.age:i;
        }
    }	
2.测试方法
    public static void main(String[] args) {
    //创建TreeSet
    TreeSet<Person> set = new TreeSet<>();
    //创建person对象
    Person person1 = new Person("tom", 29);
    Person person2 = new Person("tom", 28);
    Person person3 = new Person("jim", 38);
    //放入set
    set.add(person1);
    set.add(person2);
    set.add(person3);
    System.out.println(set);
}

2.外部比较器
    1.类不实现Comparable接口
    2.测试类创建TreeSet使用Comparator有参构造方法
    public static void main(String[] args) {
    //创建TreeSet对象,指定外部比较器
    TreeSet<Person> set = new TreeSet<>(new Comparator<Person>() {
        @Override
        public int compare(Person o1, Person o2) {
            int i = o1.getName().compareTo(o2.getName());
            return i==0?o1.getAge()-o2.getAge():i;
        }
    });
    //创建person对象
    Person person1 = new Person("tom", 29);
    Person person2 = new Person("tom", 28);
    Person person3 = new Person("jim", 38);
    //放入set
    set.add(person1);
    set.add(person2);
    set.add(person3);
    System.out.println(set);

}

五、 Map 集合

5.1 Map接口的特点

5.1.1 Map实现类的特点

  • HashMap
  • LinkedHashMap
  • HashTable
  • ConcurrentHashMap
  • TreeMap

5.2 Map 接口常用方法

方法 说明
put(K key, V value) put(K key, V value)
void putAll(Map<? extends K, ? extends V> m) 向集合中添加指定集合中所有的键——值映射关系
boolean containsKey(Object key) 判断此集合中是否包含指定的键映射关系
boolean containsValue(Object value) 判断此集合中是否包含指定的值映射关系
V get(Object key) 返回指定的键所映射的值,否则返回null
Set keySet() 以Set集合的形式返回该集合中的所有键对象
Collection values() 以Collection集合的形式返回该集合中的所有值对象
V remove(Object key) 删除并返回键对应的值对象
boolean isEmpty() 判断集合是否为空
int size() 返回集合中键——值映射关系的个数
boolean equals(Object o) 比较指定的键——值映射关系是否相等
void clear() 清空集合中所有的映射关系

5.3 HashMap

5.2.1 HashMap 特点

  • 底层实现1.7之前:数组+链表 1.8以后:数组+链表+红黑树
  • key不允许重复,如果key的值相同,后添加的数据会覆盖之前的数据
  • HashMap是非线程安全的

5.4 TreeMap

5.4.1 TreeMap 特点

  • TreeMap基于红黑树数据结构的实现
  • 键可以使用Comparable或Comparator接口, 重写compareTo方法来排序。
  • 自定义的类必须实现接口和重写方法,否则抛异
  • Key值不允许重复,如果重复会把原有的value值覆盖。

5.4.2 排序方法

1.基于JDK写好的实现了Comparable接口的实体类对象排序例如String

public static void main(String[] args) {
    //创建TreeMap对象
    TreeMap<String, String> map = new TreeMap<>();
    //增
    map.put("b", "b的value");
    map.put("a", "a的value");
    map.put("cc", "cc的value");
    map.put("c", "c的value");
    System.out.println("map = " + map);
}

2.自定义类是实现Comparable接口的内部比较器

  1. 自定义实现Comparable接口,重写compareTo(Object o){}
   import java.util.TreeMap;
   
   public class TestPerson {
       public static void main(String[] args) {
           //创建TreeMap对象
           TreeMap<Person, String> map = new TreeMap<>();
           //增
           map.put(new Person("王东阳", 20), "小男神");
           map.put(new Person("李浩", 20), "小帅哥");
           map.put(new Person("范菲菲", 19), "小美女");
           //输出
           System.out.println(map);
       }
   }
  1. 外部比较器

    Person不实现Comparable接口,在TreeMap的构造方法实现

   import java.util.Comparator;
   import java.util.TreeMap;
   import java.util.TreeSet;
   
   public class TestPerson {
       public static void main(String[] args) {
           //创建TreeMap对象
           TreeMap<Person, String> map = new TreeMap<>(new Comparator<Person>() {
               @Override
               public int compare(Person o1, Person o2) {
                   int i = o1.getAge() - o2.getAge();
                   return i==0?o1.getName().compareTo(o2.getName()):i;
               }
           });
           //增
           map.put(new Person("王东阳", 20), "小男神");
           map.put(new Person("李浩", 20), "小帅哥");
           map.put(new Person("范菲菲", 19), "小美女");
           //输出
           System.out.println(map);
       }
   }

5.4.23遍历TreeMap集合的方法

  1. TreeSet

    public static void main(String[] args) {
        //创建TreeMap对象
        TreeMap<String, String> map = new TreeMap<>();
        //增
        map.put("b", "b的value");
        map.put("a", "a的value");
        map.put("cc", "cc的value");
        map.put("c", "c的value");
        //1.keySet
        Set<String> keySet = map.keySet();
        for (String key : keySet) {
            System.out.println(key+":"+map.get(key));
        }
        System.out.println("-----------------------");
        //iterator
        Iterator<String> iterator = keySet.iterator();
        while (iterator.hasNext()){
            String key = iterator.next();
            System.out.println(key+":"+map.get(key));
        }
    }
    
  2. EntrySet

    public static void main(String[] args) {
        //创建TreeMap对象
        TreeMap<String, String> map = new TreeMap<>();
        //增
        map.put("b", "b的value");
        map.put("a", "a的value");
        map.put("cc", "cc的value");
        map.put("c", "c的value");
        //2.entrySet
        Set<Map.Entry<String, String>> entrySet = map.entrySet();
        for (Map.Entry<String, String> entry : entrySet) {
            System.out.println(entry.getKey()+":"+entry.getValue());
        }
        System.out.println("-------------------");
        Iterator<Map.Entry<String, String>> iterator = entrySet.iterator();
        while (iterator.hasNext()){
            Map.Entry<String, String> entry = iterator.next();
            System.out.println(entry.getKey()+"="+entry.getValue());
        }
    }
    

5.5 HashTable

5.5.1 HashTable 特点

  • 和Vector类似,Map体系也有一个自JDK1.2之前遗留的集合工具:Hashtable
  • HashMap和HashMap的区别在于:
    • Hashtable是线程安全的,而HashMap是非线程安全的
    • Hashtable不允许空的键值对,而HashMap可以
    • Hashtable与HashMap都实现Map接口,但二个类的继承的父类不是同一个
  • HashTable底层实现:数组+链表+红黑树
  • 常用方法:同HashMap方法

5.6 ConcurrentHashMap

5.6.1 ConcurrentHashMap 特点

  • ConcurrentHashMap是线程安全并且高效的HashMap

  • 常用方法:同HashMap

  • 数据结构:JDK8 数组+链表+红黑树,数据结构可能是链表,也可能是红黑树,红黑树是为了提高查找效率。采用CAS+Synchronized保证线程安全。

六、 总结各集合类之间的对比

Arraylist LinkedList HashSet TreeSet HashMap TreeMap



有序 有序 无序 有序 无序 有序



集合 集合 集合 集合 键值对 键值对
线








键值唯一
相同覆盖
键值唯一
相同覆盖






null
key否
value是
key是
value是





数组 链表 哈希表 二叉树 哈希表 红黑树

查询快,增删慢 查询慢,增删快 快速查找 快速排序 插入、删除和定位元素快 按自然顺序或自定义顺序遍历快

Map集合是否能存放null值总结

集合类 key value super 说明
HashTable 不能为null 不能为null Dictionary 线程安全
ConcurrentHashMap 不能为null 不能为null AbstractMap 线程局部安全
TreeMap 不能为null 可以为null AbstractMap 线程不安全
HashMap 可以为null 可以为null AbstractMap 线程不安全
举报

相关推荐

0 条评论