arraylist的sublist()返回原列表的动态视图,修改子列表会实时影响原列表;支持set、add、remove及jdk7+的clear操作,但不支持独立序列化且需防并发修改异常。

Java 中 ArrayList 的 subList() 方法返回的是原列表的**视图(view)**,不是独立副本。对子列表的修改会直接反映到原列表上,这是关键特性。
subList() 返回的是原列表的动态视图
subList(fromIndex, toIndex) 返回一个 List 子列表,它与原 ArrayList 共享底层数据。这意味着:
- 在子列表中调用
set(i, e)、remove(i)、add(e)等操作,会实时影响原列表 - 子列表的结构变化(如
add/remove)可能导致原列表大小和元素位置改变 - 子列表不支持
clear()(会抛UnsupportedOperationException),但可逐个remove
安全修改原列表的常用方式
若目标是“截取并修改原数据”,推荐以下做法:
-
仅修改已有元素值:直接用
subList().set(i, newValue)—— 安全且高效 -
批量替换一段区间:用
subList().clear()+subList().addAll(...)(注意:clear()在ArrayList.subList()上会抛异常;应改用subList().replaceAll(...)或循环set) -
删除某段区间:调用
list.subList(from, to).clear()—— 实际可行(JDK 7+ 已支持该操作,底层调用ArrayList.removeRange()) -
插入新元素到某段开头:先
subList(0, 0).addAll(newElements)(即在子列表起始位置插入)
⚠️ 注意事项和常见陷阱
使用 subList() 时需警惕:
-
并发修改异常:若原列表被其他线程结构性修改(如
add/remove),再访问子列表会触发ConcurrentModificationException -
索引越界检查严格:子列表的
fromIndex和toIndex必须在原列表范围内,且from ≤ to;越界立即抛IndexOutOfBoundsException - 子列表不可序列化独立:它没有自己的序列化逻辑,反序列化后可能失效
- 避免长期持有子列表引用:尤其在原列表频繁变更时,易引发意外行为或异常
实用示例代码
以下操作均会真实修改原 ArrayList:
<font color="#888">
List<string> list = new ArrayList(Arrays.asList("a", "b", "c", "d", "e"));
List<string> sub = list.subList(1, 4); // ["b", "c", "d"]
sub.set(0, "X"); // list → ["a", "X", "c", "d", "e"]
sub.add("Y"); // list → ["a", "X", "c", "d", "Y", "e"]
sub.remove(2); // list → ["a", "X", "d", "Y", "e"]
sub.clear(); // list → ["a", "e"] (JDK 7+ 支持)
</string></string></font>Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











