Collection与List集合
Java基础:Collection与List集合
聚焦单列集合Collection及其子体系List,核心特性、常用API、遍历方式、底层原理与实战用法
一、集合基础概述
数组是Java基础容器,但长度固定,无法适配动态数据存储;而集合是Java提供的动态容器,长度可变,支持灵活的增删改查,是开发中最常用的数据存储工具。
Java集合分为两大核心体系:
- 单列集合(Collection):每个元素仅存储一个值
- 双列集合(Map):每个元素为键值对(key-value)
二、Collection 单列集合
2.1 集合体系分支
Collection 是所有单列集合的顶层接口,两大核心子接口:
- List 系列:有序、可重复、有索引
实现类:ArrayList、LinkedList - Set 系列:无序、不重复、无索引
实现类:HashSet、TreeSet
2.2 基础特性演示
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
public class CollectionTest {
public static void main(String[] args) {
// List:有序、可重复、有索引
List<String> list = new ArrayList<>();
list.add("Java");
list.add("Java");
list.add("C++");
System.out.println(list); // [Java, Java, C++]
// Set:无序、不重复、无索引
Set<String> set = new HashSet<>();
set.add("Java");
set.add("Java");
set.add("C++");
System.out.println(set); // [Java, C++]
}
}2.3 Collection 通用API
作为顶层接口,Collection 定义的方法所有单列集合通用,核心方法如下:
| 方法名 | 功能说明 |
|---|---|
boolean add(E e) | 添加元素 |
void clear() | 清空集合 |
boolean remove(E e) | 删除指定元素 |
boolean contains(Object obj) | 判断是否包含指定元素 |
boolean isEmpty() | 判断集合是否为空 |
int size() | 获取元素个数 |
Object[] toArray() | 集合转数组 |
API 实战代码
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
public class CollectionApiTest {
public static void main(String[] args) {
Collection<String> coll = new ArrayList<>();
// 1. 添加元素
coll.add("张三");
coll.add("李四");
coll.add("王五");
System.out.println(coll); // [张三, 李四, 王五]
// 2. 元素个数
System.out.println(coll.size()); // 3
// 3. 删除元素
coll.remove("李四");
System.out.println(coll); // [张三, 王五]
// 4. 判断包含
System.out.println(coll.contains("张三")); // true
// 5. 集合转数组
Object[] arr = coll.toArray();
System.out.println(Arrays.toString(arr)); // [张三, 王五]
// 6. 清空集合
coll.clear();
System.out.println(coll.isEmpty()); // true
}
}2.4 Collection 三种遍历方式
遍历是集合最常用操作,Java 提供3种标准遍历方案,仅遍历不修改时均可使用。
方式1:迭代器遍历(集合专属)
迭代器 Iterator 是集合遍历的原生方式,核心方法:
hasNext():判断是否有下一个元素next():获取当前元素并后移指针
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
public class IteratorTest {
public static void main(String[] args) {
Collection<String> coll = new ArrayList<>();
coll.add("张无忌");
coll.add("玄冥二老");
coll.add("宋青书");
// 获取迭代器
Iterator<String> it = coll.iterator();
// 循环遍历
while (it.hasNext()) {
String name = it.next();
System.out.println(name);
}
}
}⚠️ 注意:越界调用 next() 会抛出 NoSuchElementException 异常。
方式2:增强for循环(简化迭代器)
语法简洁,本质是迭代器的语法糖,支持集合+数组:
import java.util.ArrayList;
import java.util.Collection;
public class ForEachTest {
public static void main(String[] args) {
Collection<String> coll = new ArrayList<>();
coll.add("张无忌");
coll.add("玄冥二老");
// 增强for遍历
for (String name : coll) {
System.out.println(name);
}
}
}方式3:Lambda 表达式遍历(JDK8+)
极简写法,基于函数式编程:
import java.util.ArrayList;
import java.util.Collection;
public class LambdaTest {
public static void main(String[] args) {
Collection<String> coll = new ArrayList<>();
coll.add("张无忌");
coll.add("玄冥二老");
// Lambda 遍历
coll.forEach(System.out::println);
}
}2.5 并发修改异常解决方案
异常场景
遍历集合时,直接增删元素会触发 ConcurrentModificationException 并发修改异常。
核心解决方案(3种)
- 索引for循环:删除后
i--修正索引 - 倒序索引遍历:无需修正索引
- 迭代器自带
remove()方法(推荐)
⚠️ 禁止:增强for、Lambda 遍历中增删元素
实战代码
import java.util.ArrayList;
import java.util.Iterator;
public class ModifyTest {
public static void main(String[] args) {
ArrayList<String> list = new ArrayList<>();
list.add("Java入门");
list.add("宁夏枸杞");
list.add("黑枸杞");
// 方案1:迭代器删除(无异常)
Iterator<String> it = list.iterator();
while (it.hasNext()) {
String s = it.next();
if (s.contains("枸杞")) {
it.remove(); // 迭代器原生删除
}
}
System.out.println(list); // [Java入门]
}
}三、List 集合(Collection 子接口)
List 继承 Collection,独有索引特性,是开发中使用频率最高的集合。
3.1 List 核心特性
- 有序:元素存储顺序与取出顺序一致
- 可重复:允许存储重复元素
- 有索引:支持通过索引精准操作元素
3.2 List 独有索引API
List 新增索引相关方法,Collection 无此功能:
| 方法名 | 功能说明 |
|---|---|
void add(int index, E e) | 指定索引插入元素 |
E remove(int index) | 删除指定索引元素,返回被删元素 |
E set(int index, E e) | 修改指定索引元素,返回原元素 |
E get(int index) | 获取指定索引元素 |
API 实战
import java.util.ArrayList;
import java.util.List;
public class ListApiTest {
public static void main(String[] args) {
List<String> list = new ArrayList<>();
list.add("张三");
list.add("李四");
// 索引插入
list.add(1, "赵敏");
System.out.println(list); // [张三, 赵敏, 李四]
// 索引删除
list.remove(2);
System.out.println(list); // [张三, 赵敏]
// 索引修改+获取
list.set(0, "金毛狮王");
System.out.println(list.get(0)); // 金毛狮王
}
}3.3 List 四种遍历方式
在 Collection 三种遍历基础上,新增普通for索引遍历:
- 普通for(索引)
- 迭代器
- 增强for
- Lambda
// 普通for索引遍历(List专属)
for (int i = 0; i < list.size(); i++) {
System.out.println(list.get(i));
}3.4 List 两大实现类对比
1. ArrayList(数组实现)
- 底层:动态数组
- 特性:查询快、增删慢(首尾增删除外)
- 场景:高频查询、少量增删(开发首选)
2. LinkedList(双链表实现)
- 底层:双向链表
- 特性:查询慢、首尾增删极快
- 场景:高频首尾操作、模拟队列/栈
3.5 LinkedList 实战:队列 & 栈
利用 LinkedList 首尾操作特性,快速实现经典数据结构:
- 队列:先进先出(FIFO)
- 栈:后进先出(LIFO)
import java.util.LinkedList;
public class LinkedListTest {
public static void main(String[] args) {
// 1. 模拟队列
LinkedList<String> queue = new LinkedList<>();
queue.addLast("A"); // 入队
queue.addLast("B");
System.out.println(queue.removeFirst()); // 出队 A
// 2. 模拟栈
LinkedList<String> stack = new LinkedList<>();
stack.push("1"); // 压栈
stack.push("2");
System.out.println(stack.pop()); // 弹栈 2
}
}四、总结
- Collection:单列集合顶层接口,通用增删查+3种遍历方式
- List:有序可重复有索引,独有索引API,4种遍历方式
实现类选型:
- 查多改少 → ArrayList
- 首尾增删 → LinkedList
- 避坑指南:遍历增删用迭代器,禁止增强for/Lambda直接修改集合