一. 概述
集合、数组都对多个数据进行存储操作的结构,称为Java容器
集合解决了数组长度不可修改、元素增删改查效率低、不能满足无序不可重复元素等缺点
Java集合分为Collection和Map两种体系
- Collection接口:单列数据,定义存取一组对象的方法的集合
- Map接口:双列数据,保存具有映射关系的"key-value对"的集合
二. Collection

1. Collection接口
Collection接口的常用方法:
- add(E e)------------------------------------------增
- addAll(Collection<? extends E> c)
- clear()
- contains(Object o)
- containsAll(Collecetion<?> c)
- equals(Object o)
- hashCode()
- isEmpty()
- iterator()-------------------------------------------遍历
- remove(Object o)-------------------------------删
- removeAll(Collection<?> c) ----------------差集
- retainAll(Collection<?> c) -------------------交集
- size()
- toArray()
- toArray(T[] a)
Collection只是接口,具体方法由子类ArrayList或LinkedList实现,即
Collection c = new ArrayList(); ---------多态的体现
Collection集合与数组间的转换
Collection c = new ArrayList();
c.add("abc");
c.add("123");
c.add("你好");
System.out.println(c);
Object[] arr = c.toArray(); //集合 -> 数组 toArray()
//这里使用数组方式遍历,推荐使用迭代器或增强for循环
for(int i = 0; i < arr.length; i++){
System.out.println(arr[i]);
}
List list = Arrays.asList(arr); //数组 -> 集合 Arrays.asList()
System.out.println(list);
迭代器Iterator和for-each
Iterator主要用于Collection集合遍历,实现代码如下:
//迭代器
Iterator iterator = c.iterator();
while(iterator.hasNext()){
System.out.println(iterator.next());
}
//增强for循环
for(Object o : c){ //for(集合元素的类型 局部变量 : 集合对象)
System.out.println(o);
}
2. List接口(有序,可重复)
- ArrayList:底层数据结构是动态数组,查询快,增删慢,线程不安全,效率高
- LinkedList:底层数据结构是双向链表,查询慢,增删快,线程不安全,效率高
除了Collection继承的方法,List接口增加了以下常用方法:
- add(int index, E element)--------------------------------------插
- addAll(int index, Collection<? extends E> c)
- get(int index)------------------------------------------------------查
- indexOf(Object o)
- lastIndexOf(Object o)
- remove(int index)------------------------------------------------删
- set(int index, E element)---------------------------------------改
- subList(int fromIndex, int toIndex)
问题1:什么时候用ArrayList?什么时候用LinkedList?为什么?
ArrayList适合查找或遍历数据,LinkedList适合动态插入和删除数据
数组可以随机访问,适合查找,链表只能顺序访问,不适合查找
数组有大小限制,不适合增删,链表没有大小限制,适合增删
总之,对于List,增删用LinkedList,查改用ArrayList
3. Set接口(无序,不可重复)
- HashSet:基于哈希表,支持快速查找,不支持有序性操作,线程不安全,效率高
- LinkedHashSet:具有 HashSet 的查找效率,并且内部使用双向链表维护元素的插入顺序
- TreeSet:基于红黑树,支持有序性操作,在一个范围查找元素,但查找效率不如HashSet
Set继承Collecetion的方法,没有提供额外的方法
HashSet 源码
public class HashSet<E>
extends AbstractSet<E>
implements Set<E>, Cloneable, java.io.Serializable
{
@java.io.Serial
static final long serialVersionUID = -5024744406713321676L;
private transient HashMap<E,Object> map;
private static final Object PRESENT = new Object();
public HashSet() {
map = new HashMap<>();
}
...
public boolean add(E e) {
return map.put(e, PRESENT)==null;
}
...
}
可以看到,HashSet利用HashMap对象存储Map数据,方法也是调用map的方法
三. Map

- HashMap:根据键的哈希值存储键值对(key-value)映射,线程不安全,访问速度快
- LinkedHashMap:继承于HashMap,使用双向链表根据元素的自然顺序进行排序
- TreeMap:基于红黑树
- HashTable(过时):它是线程安全的,现在使用 ConcurrentHashMap 来支持线程安全

本文深入解析Java容器体系,包括Collection和Map两大类。详细介绍List、Set、Map的不同接口及其实现类,如ArrayList、LinkedList、HashSet、HashMap等,对比其性能特点,适用于不同场景的数据存储需求。

被折叠的 条评论
为什么被折叠?



