文章首发于:clawhub.club


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
/**
* Appends all of the elements in the specified collection to the end of
* this list, in the order that they are returned by the
* specified collection's Iterator. The behavior of this operation is
* undefined if the specified collection is modified while the operation
* is in progress. (This implies that the behavior of this call is
* undefined if the specified collection is this list, and this
* list is nonempty.)
* 将指定集合中所有的元素添加到列表末尾,按照指定集合中迭代器的顺序返回元素。
* 如果指定集合在操作过程中被修改了,那么这个操作(方法)的行为时不确定的。
* (这意味着如果指定集合是这个列表,并且这个列表不为空,调用此方法是不确定的)
*
* @param c collection containing elements to be added to this list
* c 参数为要添加到列表中包含元素的集合
* @return <tt>true</tt> if this list changed as a result of the call
* 如果列表作为调用的结果被改变了,则返回 ture
* @throws NullPointerException if the specified collection is null
* 抛出 NullPointerException 异常,如果指定集合为 null
*/
public boolean addAll(Collection<? extends E> c) {
// 集合转数组
Object[] a = c.toArray();
// 集合中的元素个数,也即是 Object 数组的长度
int numNew = a.length;
// 确保在 ArrayList 实例的 size 基础上加上集合的元素个数,容量仍然充足
ensureCapacityInternal(size + numNew); // Increments modCount
// 使用 System.arraycopy 方法实现添加集合中的元素
System.arraycopy(a, 0, elementData, size, numNew);
// ArrayList 的 size 要加上新增的元素个数
size += numNew;
// 返回新增元素个数是否不等于 0
return numNew != 0;
}

/**
* Inserts all of the elements in the specified collection into this
* list, starting at the specified position. Shifts the element
* currently at that position (if any) and any subsequent elements to
* the right (increases their indices). The new elements will appear
* in the list in the order that they are returned by the
* specified collection's iterator.
* 从指定位置开始,将指定集合中的所有元素插入了列表中。
* 移动先前位置的元素(如果有的话)以及任何后续的元素到右边(增加它们的索引)。
* 新元素将按照指定集合中​​迭代器返回的顺序出现在列表中。
*
* @param index index at which to insert the first element from the
* specified collection
* index 参数为从指定集合中插入的第一个元素的索引
* @param c collection containing elements to be added to this list
* c 参数为要添加到列表中包含元素的集合
* @return <tt>true</tt> if this list changed as a result of the call
* 如果列表作为调用的结果被改变了,则返回 ture
* @throws IndexOutOfBoundsException {@inheritDoc}
* 抛出 IndexOutOfBoundsException 异常
* @throws NullPointerException if the specified collection is null
* 抛出 NullPointerException 异常,如果指定集合为 null
*/
public boolean addAll(int index, Collection<? extends E> c) {
// add 操作的边界检查
rangeCheckForAdd(index);
// 集合转数组
Object[] a = c.toArray();
// 数组长度
int numNew = a.length;
// 确保在 ArrayList 实例的 size 基础上加上集合的元素个数,容量仍然充足
ensureCapacityInternal(size + numNew); // Increments modCount

// 要移动的元素的个数
int numMoved = size - index;
if (numMoved > 0)
System.arraycopy(elementData, index, elementData, index + numNew,
numMoved);
// 使用 System.arraycopy 方法实现添加集合中的元素
System.arraycopy(a, 0, elementData, index, numNew);
// ArrayList 的 size 要加上新增的元素个数
size += numNew;
// 返回新增元素个数是否不等于 0
return numNew != 0;
}

/**
* Removes from this list all of the elements whose index is between
* {@code fromIndex}, inclusive, and {@code toIndex}, exclusive.
* Shifts any succeeding elements to the left (reduces their index).
* This call shortens the list by {@code (toIndex - fromIndex)} elements.
* (If {@code toIndex==fromIndex}, this operation has no effect.)
* 删除列表中从 fromIndex(包含)到 toIndex(不包含)索引对应元素
* 移动任何后续的元素到左边(减少它们的索引)。
* 慈此调用通过删除 toIndex - fromIndex 之间的元素缩短列表。
* 如果 toIndex == fromIndex 的话,此操作无效
*
* @throws IndexOutOfBoundsException if {@code fromIndex} or
* {@code toIndex} is out of range
* ({@code fromIndex < 0 ||
* fromIndex >= size() ||
* toIndex > size() ||
* toIndex < fromIndex})
* 下面几种情况会抛出 IndexOutOfBoundsException 异常。
* 如果 fromIndex 或者 toIndex 越界
* 或者 fromIndex < 0
* 或者 fromIndex >= size
* 或者 toIndex > size
* 或者 toIndex < fromIndex
*/
protected void removeRange(int fromIndex, int toIndex) {
// 修改次数加 1
modCount++;
// 计算要移动的次数
int numMoved = size - toIndex;
// 使用 System.arraycopy 方法实现元素向左移动
System.arraycopy(elementData, toIndex, elementData, fromIndex,
numMoved);

// clear to let GC do its work
// 计算新的 size 大小
int newSize = size - (toIndex-fromIndex);
// 将删除元素的引用置为 null,让垃圾回收器清除没有引用的对象
for (int i = newSize; i < size; i++) {
elementData[i] = null;
}
size = newSize;
}

/**
* Checks if the given index is in range. If not, throws an appropriate
* runtime exception. This method does *not* check if the index is
* negative: It is always used immediately prior to an array access,
* which throws an ArrayIndexOutOfBoundsException if index is negative.
* 检查是否给定的索引在范围内。如果不再,抛出适当的运行时异常。
* 这个方法不检查索引是不是负数:它(这个方法)总是在数组访问之前使用,如果索引为负数,
* 抛出 ArrayIndexOutOfBoundsException 异常
*/
private void rangeCheck(int index) {
// 判断索引是否大于等于 size,如果是,则抛出 IndexOutOfBoundsException
if (index >= size)
throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
}

/**
* A version of rangeCheck used by add and addAll.
* 被 add 和 addAll 使用的边界检查版本
*/
private void rangeCheckForAdd(int index) {
// 判断索引是否大于 size 或者小于 0(为负数),如果是,抛出IndexOutOfBoundsException 异常
if (index > size || index < 0)
throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
}

/**
* Constructs an IndexOutOfBoundsException detail message.
* Of the many possible refactorings of the error handling code,
* this "outlining" performs best with both server and client VMs.
* 构造一个 IndexOutOfBoundsException 的详细消息。
* 在错误处理代码许多可能的重构中,这种“描述”对服务器和客户端虚拟机都表现最好。
*
*/
private String outOfBoundsMsg(int index) {
// 返回一个包含当前给定的 index 和 size 的字符串
return "Index: "+index+", Size: "+size;
}

/**
* Removes from this list all of its elements that are contained in the
* specified collection.
* 移除所有指定集合中存在的元素在列表中也存在的元素
*
* @param c collection containing elements to be removed from this list
* c 参数为要从列表中删除元素的集合
* @return {@code true} if this list changed as a result of the call
* 如果列表作为调用的结果被改变了,则返回 ture
* @throws ClassCastException if the class of an element of this list
* is incompatible with the specified collection
* 抛出 ClassCastException 异常,如果此列表的元素的类与指定的集合不兼容
* (<a href="Collection.html#optional-restrictions">optional</a>)
* @throws NullPointerException if this list contains a null element and the
* specified collection does not permit null elements
* 抛出 NullPointerException 异常,如果此列表包含 null 元素,并且指定的集合不允许 null 元素
* (<a href="Collection.html#optional-restrictions">optional</a>),
* or if the specified collection is null
* @see Collection#contains(Object)
* 参看 Collection的contains(Object) 方法
*/
public boolean removeAll(Collection<?> c) {
// 使用 Objects 工具类检查 c 集合是否指向 null
Objects.requireNonNull(c);
// 根据第二个参数来判断是要删除还是要保留
return batchRemove(c, false);
}

/**
* Retains only the elements in this list that are contained in the
* specified collection. In other words, removes from this list all
* of its elements that are not contained in the specified collection.
* 保存列表中指定集合中的元素(相当于是做一个交集)。
* 换句话说,就是移除列表中有的而指定集合没有的那些元素。
*
* @param c collection containing elements to be retained in this list
* c 参数为要保留在列表中的元素集合
* @return {@code true} if this list changed as a result of the call
* 如果列表作为调用的结果被改变了,则返回 ture
* @throws ClassCastException if the class of an element of this list
* is incompatible with the specified collection
* 抛出 ClassCastException 异常,如果此列表的元素的类与指定的集合不兼容
* (<a href="Collection.html#optional-restrictions">optional</a>)
* @throws NullPointerException if this list contains a null element and the
* specified collection does not permit null elements
* 抛出 NullPointerException 异常,如果此列表包含 null 元素,
* 并且指定的集合不允许 null 元素
* (<a href="Collection.html#optional-restrictions">optional</a>),
* or if the specified collection is null
* @see Collection#contains(Object)
* 参看 Collection的contains(Object) 方法
*/
public boolean retainAll(Collection<?> c) {
// 使用 Objects 工具类检查 c 集合是否指向 null
Objects.requireNonNull(c);
// 根据第二个参数来判断是要删除还是要保留
return batchRemove(c, true);
}

// complement 为 true,保留集合中存在的元素
// complement 为 false,删除集合中存在的元素
private boolean batchRemove(Collection<?> c, boolean complement) {
final Object[] elementData = this.elementData;
int r = 0, w = 0;
boolean modified = false;
try {
for (; r < size; r++)
// 执行保留或者删除操作
if (c.contains(elementData[r]) == complement)
// 一行代码,两步操作,一步是在数组下标为 w 的位置重新赋值,另一步是 w 加 1
elementData[w++] = elementData[r];
} finally {
// Preserve behavioral compatibility with AbstractCollection,
// even if c.contains() throws.
// 保留与AbstractCollection的行为兼容性,即使 c.contains()抛出也是如此
if (r != size) {
// 移动数组
System.arraycopy(elementData, r,
elementData, w,
size - r);
w += size - r;
}
if (w != size) {
// clear to let GC do its work
// 给无用的数组元素赋 null 值,让垃圾回收器回收没有引用的对象
for (int i = w; i < size; i++)
elementData[i] = null;
// 修改次数
modCount += size - w;
// size = w
size = w;
modified = true;
}
}
return modified;
}

/**
* Save the state of the <tt>ArrayList</tt> instance to a stream (that
* is, serialize it).
* 保存 ArrayList 实例的状态到流中(也就是说,序列化它)
*
* @serialData The length of the array backing the <tt>ArrayList</tt>
* instance is emitted (int), followed by all of its elements
* (each an <tt>Object</tt>) in the proper order.
* 序列化的数据为 ArrayList 实例中数组的长度,然后是以正确顺序排列的 Object 元素
*/
private void writeObject(java.io.ObjectOutputStream s)
throws java.io.IOException{
// Write out element count, and any hidden stuff
// 写出元素计数和任何隐藏的东西,在写之前先保存修改次数,以防在写的过程中结构改变
int expectedModCount = modCount;
// 执行默认的序列化机制,写出一些隐含的信息
s.defaultWriteObject();

// Write out size as capacity for behavioural compatibility with clone()
// 写出大小作为与 clone() 方法兼容性的容量
s.writeInt(size);

// Write out all elements in the proper order.
// 以正确的顺序写出所有的元素,遍历 elementData 数组中前 size 的元素
for (int i=0; i<size; i++) {
s.writeObject(elementData[i]);
}
// 如果写入流后的修改次数和写入流前的修改次数不一致,抛出 ConcurrentModificationException 并发修改异常
if (modCount != expectedModCount) {
throw new ConcurrentModificationException();
}
}

/**
* Reconstitute the <tt>ArrayList</tt> instance from a stream (that is,
* deserialize it).
* 复原 ArrayList 实例从流中(也就是说,反序列化它)
*/
private void readObject(java.io.ObjectInputStream s)
throws java.io.IOException, ClassNotFoundException {
elementData = EMPTY_ELEMENTDATA;

// Read in size, and any hidden stuff
// 读入 size 和任何隐藏的东西,执行默认的反序列化机制,读入一些隐含的信息
s.defaultReadObject();

// Read in capacity
// 读入容量
s.readInt(); // ignored

if (size > 0) {
// be like clone(), allocate array based upon size not capacity
// 就像克隆一样,存储数组是基于 size 的而不是 capacity
int capacity = calculateCapacity(elementData, size);
// 检查数组是不是 Object 类型
SharedSecrets.getJavaOISAccess().checkArray(s, Object[].class, capacity);
// 确保这个实例的 elementData 容量充足,此时 capacity == size
ensureCapacityInternal(size);

Object[] a = elementData;
// Read in all elements in the proper order.
// 以正确的顺序读入所有元素
for (int i=0; i<size; i++) {
a[i] = s.readObject();
}
}
}

/**
* Returns a list iterator over the elements in this list (in proper
* sequence), starting at the specified position in the list.
* The specified index indicates the first element that would be
* returned by an initial call to {@link ListIterator#next next}.
* An initial call to {@link ListIterator#previous previous} would
* return the element with the specified index minus one.
* 从列表中的指定位置开始,返回列表中元素的列表迭代器(按正确顺序)。
* 指定的索引表示初始调用 ListIterator 的 next 方法将返回的第一个元素。
* 对 ListIterator 的 previous 方法的初始调用将返回指定索引减去1的元素
* <p>The returned list iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
* 返回的列表迭代器是 fail-fast 的。
*
* @throws IndexOutOfBoundsException {@inheritDoc}
* 抛出 IndexOutOfBoundsException 下表越界异常
*/
public ListIterator<E> listIterator(int index) {
// 越界检查
if (index < 0 || index > size)
throw new IndexOutOfBoundsException("Index: "+index);
return new ListItr(index);
}

/**
* Returns a list iterator over the elements in this list (in proper
* sequence).
* 返回列表中元素的列表迭代器(按正确顺序)
*
* <p>The returned list iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
* 返回的列表迭代器是 fail-fast 的。
*
* @see #listIterator(int)
* 参看 listIterator(int) 方法
*/
public ListIterator<E> listIterator() {
return new ListItr(0);
}

/**
* Returns an iterator over the elements in this list in proper sequence.
* 返回列表中元素的列表迭代器(按正确顺序)
* <p>The returned iterator is <a href="#fail-fast"><i>fail-fast</i></a>.
* 返回的列表迭代器是 fail-fast 的。
* @return an iterator over the elements in this list in proper sequence
* 返回列表中元素的列表迭代器(按正确顺序)
*/
public Iterator<E> iterator() {
return new Itr();
}

/**
* An optimized version of AbstractList.Itr
* AbstractList.Itr的优化版本,私有内部类
*/
private class Itr implements Iterator<E> {
int cursor; // index of next element to return 将要返回的下一个元素索引
int lastRet = -1; // index of last element returned; -1 if no such 上一个返回元素的索引,如果不是这样的话就是 -1
// 在迭代过程中,期望修改的次数应该始终等于修改次数,否则会抛出并发修改异常
int expectedModCount = modCount;

Itr() {}

// 判断是否有下一个元素
public boolean hasNext() {
return cursor != size;
}

// 返回迭代的下一个元素
@SuppressWarnings("unchecked")
public E next() {
// 检查修改是否不一致
checkForComodification();
// 当前要返回的元素索引
int i = cursor;
if (i >= size)
throw new NoSuchElementException();
Object[] elementData = ArrayList.this.elementData;
if (i >= elementData.length)
throw new ConcurrentModificationException();
// 下一个元素的索引
cursor = i + 1;
// 一行代码两步操作,一部是返回当前元素,另一步是将 lastRet 置为当前元素的索引
return (E) elementData[lastRet = i];
}

// 删除元素
public void remove() {
// remove() 方法要在 next() 方法之后使用,否则会抛出 IllegalStateException 异常
if (lastRet < 0)
throw new IllegalStateException();
// 检查修改是否不一致
checkForComodification();

try {
// ArrayList 本身的 remove(int) 方法
ArrayList.this.remove(lastRet);
cursor = lastRet;
lastRet = -1;
// 更改期望的元素修改次数
expectedModCount = modCount;
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}

@Override
@SuppressWarnings("unchecked")
public void forEachRemaining(Consumer<? super E> consumer) {
Objects.requireNonNull(consumer);
final int size = ArrayList.this.size;
int i = cursor;
if (i >= size) {
return;
}
final Object[] elementData = ArrayList.this.elementData;
if (i >= elementData.length) {
throw new ConcurrentModificationException();
}
while (i != size && modCount == expectedModCount) {
consumer.accept((E) elementData[i++]);
}
// update once at end of iteration to reduce heap write traffic
// 在迭代结束时更新一次以减少堆写入容量
cursor = i;
lastRet = i - 1;
checkForComodification();
}

// 检查并发修改异常
final void checkForComodification() {
if (modCount != expectedModCount)
throw new ConcurrentModificationException();
}
}

/**
* An optimized version of AbstractList.ListItr
* AbstractList.ListItr的优化版本,私有内部类
*/
private class ListItr extends Itr implements ListIterator<E> {
// 带参构造方法
ListItr(int index) {
super();
cursor = index;
}

// 是否有上一个元素
public boolean hasPrevious() {
return cursor != 0;
}

// 返回下一个元素的索引
public int nextIndex() {
return cursor;
}

// 返回上一个元素的索引
public int previousIndex() {
return cursor - 1;
}

@SuppressWarnings("unchecked")
// 返回上一个元素
public E previous() {
// 检查修改异常
checkForComodification();
// 计算上一个元素的索引
int i = cursor - 1;
if (i < 0)
throw new NoSuchElementException();
Object[] elementData = ArrayList.this.elementData;
if (i >= elementData.length)
throw new ConcurrentModificationException();
// 下一个元素为当前元素
cursor = i;
// 返回上一个元素
return (E) elementData[lastRet = i];
}

// 修改元素值
public void set(E e) {
if (lastRet < 0)
throw new IllegalStateException();
// 检查修改异常
checkForComodification();

try {
ArrayList.this.set(lastRet, e);
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}

// 添加元素值
public void add(E e) {
// 检查修改异常
checkForComodification();

try {
// 在当前元素的下一个位置添加新元素
int i = cursor;
ArrayList.this.add(i, e);
cursor = i + 1;
lastRet = -1;
expectedModCount = modCount;
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}
}

/**
* Returns a view of the portion of this list between the specified
* {@code fromIndex}, inclusive, and {@code toIndex}, exclusive. (If
* {@code fromIndex} and {@code toIndex} are equal, the returned list is
* empty.) The returned list is backed by this list, so non-structural
* changes in the returned list are reflected in this list, and vice-versa.
* The returned list supports all of the optional list operations.
* 返回指定的 fromIndex(包含该位置的值) 和 toIndex(不包含该位置的值) 之间的此列表的视图
* (如果 fromIndex == toIndex ,则返回的列表为空)
* 返回的列表是依赖于此列表的,因此在对返回列表的非结构化更改会反映到此列表中,反之亦然(就是说对两者任一方的更改都会影响另一方)。
* 返回的列表支持列表所有的操作。
*
* <p>This method eliminates the need for explicit range operations (of
* the sort that commonly exist for arrays). Any operation that expects
* a list can be used as a range operation by passing a subList view
* instead of a whole list. For example, the following idiom
* removes a range of elements from a list:
* <pre>
* list.subList(from, to).clear();
* </pre>
* 此方法消除了对显式范围方法的需要(通常还需要对数组进行排序)
* 任何需要对整个列表部分的操作都可以传递 subList,而不是对整个列表进行操作(提高性能)。例如,下面的语句是从列表中删除一系列元素:list.subList(from, to).clear();
*
*
* Similar idioms may be constructed for {@link #indexOf(Object)} and
* {@link #lastIndexOf(Object)}, and all of the algorithms in the
* {@link Collections} class can be applied to a subList.
* 可以为 indexOf(Object)和 lastIndexOf(Object)构造类似的语句,Collections类中的所有算法都可以应用于 subList。
*
* <p>The semantics of the list returned by this method become undefined if
* the backing list (i.e., this list) is <i>structurally modified</i> in
* any way other than via the returned list. (Structural modifications are
* those that change the size of this list, or otherwise perturb it in such
* a fashion that iterations in progress may yield incorrect results.)
* 如果依赖列表(进行操作的列表)通过返回的列表以外的方式对结构进行修改,那么通过这个方法返回的列表就被变得不确定。
* (结构化修改是指改变了这个列表的大小,或者其他扰乱列表的方式,使得正在进行的迭代可能产生不正确的结果)
*
* @throws IndexOutOfBoundsException {@inheritDoc}
* 抛出 IndexOutOfBoundsException 下表越界异常
* @throws IllegalArgumentException {@inheritDoc}
* 抛出 IllegalArgumentException 非法参数异常
*/
public List<E> subList(int fromIndex, int toIndex) {
// 检查返回列表的边界
subListRangeCheck(fromIndex, toIndex, size);
return new SubList(this, 0, fromIndex, toIndex);
}

// 返回列表边界检查
static void subListRangeCheck(int fromIndex, int toIndex, int size) {
if (fromIndex < 0)
throw new IndexOutOfBoundsException("fromIndex = " + fromIndex);
if (toIndex > size)
throw new IndexOutOfBoundsException("toIndex = " + toIndex);
if (fromIndex > toIndex)
throw new IllegalArgumentException("fromIndex(" + fromIndex +
") > toIndex(" + toIndex + ")");
}

// SubList 继承自 AbstractList,并没有存储实际元素数据,而是存储的索引数据
private class SubList extends AbstractList<E> implements RandomAccess {
private final AbstractList<E> parent; // 父列表,也即是产生 subList 的列表
private final int parentOffset; // 相对于父列表的偏移值
private final int offset; // 相对于子列表自己的偏移值
int size; // 子列表的大小

// 有参构造方法
SubList(AbstractList<E> parent,
int offset, int fromIndex, int toIndex) {
this.parent = parent;
this.parentOffset = fromIndex;
this.offset = offset + fromIndex;
this.size = toIndex - fromIndex;
this.modCount = ArrayList.this.modCount;
}

// 修改方法,返回修改前的值
public E set(int index, E e) {
rangeCheck(index);
checkForComodification();
E oldValue = ArrayList.this.elementData(offset + index);
ArrayList.this.elementData[offset + index] = e;
return oldValue;
}

// 根据索引获取元素
public E get(int index) {
rangeCheck(index);
checkForComodification();
return ArrayList.this.elementData(offset + index);
}

// 获取子列表的 size 大小
public int size() {
checkForComodification();
return this.size;
}

// 添加元素,对父列表和子列表都会造成影响
public void add(int index, E e) {
rangeCheckForAdd(index);
checkForComodification();
parent.add(parentOffset + index, e);
this.modCount = parent.modCount;
this.size++;
}

// 根据索引移除元素,并返回移除的值,对父列表和子列表都会造成影响
public E remove(int index) {
rangeCheck(index);
checkForComodification();
E result = parent.remove(parentOffset + index);
this.modCount = parent.modCount;
this.size--;
return result;
}

// 移除指定索引范围内(不包括后面的索引)的元素,实际调用的还是父列表中的 removeRange 方法
protected void removeRange(int fromIndex, int toIndex) {
checkForComodification();
parent.removeRange(parentOffset + fromIndex,
parentOffset + toIndex);
this.modCount = parent.modCount;
this.size -= toIndex - fromIndex;
}

// 添加指定集合中的所有元素到子列表末尾,是调用 SubList 类中的 addAll 方法实现的
public boolean addAll(Collection<? extends E> c) {
return addAll(this.size, c);
}

// 从指定的子列表中的索引位置添加集合中的所有元素
public boolean addAll(int index, Collection<? extends E> c) {
rangeCheckForAdd(index);
int cSize = c.size();
if (cSize==0)
return false;

checkForComodification();
parent.addAll(parentOffset + index, c);
this.modCount = parent.modCount;
this.size += cSize;
return true;
}

// 返回子列表的迭代器
public Iterator<E> iterator() {
return listIterator();
}

// 返回子列表的列表迭代器
public ListIterator<E> listIterator(final int index) {
checkForComodification();
rangeCheckForAdd(index);
final int offset = this.offset;

// 返回一个实现 ListIterator 的实现类
return new ListIterator<E>() {
int cursor = index;
int lastRet = -1;
int expectedModCount = ArrayList.this.modCount;

public boolean hasNext() {
return cursor != SubList.this.size;
}

@SuppressWarnings("unchecked")
public E next() {
checkForComodification();
int i = cursor;
if (i >= SubList.this.size)
throw new NoSuchElementException();
Object[] elementData = ArrayList.this.elementData;
if (offset + i >= elementData.length)
throw new ConcurrentModificationException();
cursor = i + 1;
return (E) elementData[offset + (lastRet = i)];
}

public boolean hasPrevious() {
return cursor != 0;
}

@SuppressWarnings("unchecked")
public E previous() {
checkForComodification();
int i = cursor - 1;
if (i < 0)
throw new NoSuchElementException();
Object[] elementData = ArrayList.this.elementData;
if (offset + i >= elementData.length)
throw new ConcurrentModificationException();
cursor = i;
return (E) elementData[offset + (lastRet = i)];
}

@SuppressWarnings("unchecked")
public void forEachRemaining(Consumer<? super E> consumer) {
Objects.requireNonNull(consumer);
final int size = SubList.this.size;
int i = cursor;
if (i >= size) {
return;
}
final Object[] elementData = ArrayList.this.elementData;
if (offset + i >= elementData.length) {
throw new ConcurrentModificationException();
}
while (i != size && modCount == expectedModCount) {
consumer.accept((E) elementData[offset + (i++)]);
}
// update once at end of iteration to reduce heap write traffic
lastRet = cursor = i;
checkForComodification();
}

public int nextIndex() {
return cursor;
}

public int previousIndex() {
return cursor - 1;
}

public void remove() {
if (lastRet < 0)
throw new IllegalStateException();
checkForComodification();

try {
SubList.this.remove(lastRet);
cursor = lastRet;
lastRet = -1;
expectedModCount = ArrayList.this.modCount;
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}

public void set(E e) {
if (lastRet < 0)
throw new IllegalStateException();
checkForComodification();

try {
ArrayList.this.set(offset + lastRet, e);
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}

public void add(E e) {
checkForComodification();

try {
int i = cursor;
SubList.this.add(i, e);
cursor = i + 1;
lastRet = -1;
expectedModCount = ArrayList.this.modCount;
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}

final void checkForComodification() {
if (expectedModCount != ArrayList.this.modCount)
throw new ConcurrentModificationException();
}
};
}

// SubList 的 subList 方法
public List<E> subList(int fromIndex, int toIndex) {
subListRangeCheck(fromIndex, toIndex, size);
return new SubList(this, offset, fromIndex, toIndex);
}

// 边界检查
private void rangeCheck(int index) {
if (index < 0 || index >= this.size)
throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
}

// 为添加操作的编边界检查
private void rangeCheckForAdd(int index) {
if (index < 0 || index > this.size)
throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
}

// 越过边界时的消息封装
private String outOfBoundsMsg(int index) {
return "Index: "+index+", Size: "+this.size;
}

// 检查并发修改异常
private void checkForComodification() {
if (ArrayList.this.modCount != this.modCount)
throw new ConcurrentModificationException();
}

// 返回分裂迭代器
public Spliterator<E> spliterator() {
checkForComodification();
return new ArrayListSpliterator<E>(ArrayList.this, offset,
offset + this.size, this.modCount);
}
}

@Override
// Java8 Lambda 表达式遍历列表元素方式
public void forEach(Consumer<? super E> action) {
Objects.requireNonNull(action);
final int expectedModCount = modCount;
@SuppressWarnings("unchecked")
final E[] elementData = (E[]) this.elementData;
final int size = this.size;
for (int i=0; modCount == expectedModCount && i < size; i++) {
action.accept(elementData[i]);
}
if (modCount != expectedModCount) {
throw new ConcurrentModificationException();
}
}

@Override
// 过滤器删除元素
public boolean removeIf(Predicate<? super E> filter) {
Objects.requireNonNull(filter);
// figure out which elements are to be removed
// any exception thrown from the filter predicate at this stage
// will leave the collection unmodified
// 找出要删除哪些元素在此阶段从过滤谓词,抛出的任何异常都将使集合保持不变

int removeCount = 0;
final BitSet removeSet = new BitSet(size);
final int expectedModCount = modCount;
final int size = this.size;
for (int i=0; modCount == expectedModCount && i < size; i++) {
@SuppressWarnings("unchecked")
final E element = (E) elementData[i];
if (filter.test(element)) {
removeSet.set(i);
removeCount++;
}
}
if (modCount != expectedModCount) {
throw new ConcurrentModificationException();
}

// shift surviving elements left over the spaces left by removed elements
// 向左移动后续的元素
final boolean anyToRemove = removeCount > 0;
if (anyToRemove) {
final int newSize = size - removeCount;
for (int i=0, j=0; (i < size) && (j < newSize); i++, j++) {
i = removeSet.nextClearBit(i);
elementData[j] = elementData[i];
}
for (int k=newSize; k < size; k++) {
elementData[k] = null; // Let gc do its work
}
this.size = newSize;
if (modCount != expectedModCount) {
throw new ConcurrentModificationException();
}
modCount++;
}

return anyToRemove;
}

@Override
@SuppressWarnings("unchecked")
// 根据操作符替换列表中的所有与元素值
public void replaceAll(UnaryOperator<E> operator) {
Objects.requireNonNull(operator);
final int expectedModCount = modCount;
final int size = this.size;
for (int i=0; modCount == expectedModCount && i < size; i++) {
elementData[i] = operator.apply((E) elementData[i]);
}
if (modCount != expectedModCount) {
throw new ConcurrentModificationException();
}
modCount++;
}

@Override
@SuppressWarnings("unchecked")
// 根据比较器排序
public void sort(Comparator<? super E> c) {
final int expectedModCount = modCount;
Arrays.sort((E[]) elementData, 0, size, c);
if (modCount != expectedModCount) {
throw new ConcurrentModificationException();
}
modCount++;
}
}