1700444440
1700444441
}
1700444442
1700444443
其中的checkForComodification方法就是用于检测是否并发修改的,代码如下:
1700444444
1700444445
private void checkForComodification(){
1700444446
1700444447
//判断当前修改计数器是否与子列表生成时一致
1700444448
1700444449
if(l.modCount!=expectedModCount)
1700444450
1700444451
throw new ConcurrentModificationException();
1700444452
1700444453
}
1700444454
1700444455
expectedModCount是从什么地方来的呢?它是在SubList子列表的构造函数中赋值的,其值等于生成子列表时的修改次数(modCount变量)。因此在生成子列表后再修改原始列表,l.modCount的值就必然比expectedModCount大1,不再保持相等了,于是也就抛出了ConcurrentModificationException异常。
1700444456
1700444457
subList的其他方法也会检测修改计数器,例如set、get、add等方法,若生成子列表后,再修改原列表,这些方法也会抛出ConcurrentModificationException异常。
1700444458
1700444459
对于子列表操作,因为视图是动态生成的,生成子列表后再操作原列表,必然会导致“视图”的不稳定,最有效的办法就是通过Collections.unmodifiableList方法设置列表为只读状态,代码如下:
1700444460
1700444461
public static void main(String[]args){
1700444462
1700444463
List<String>list=new ArrayList<String>();
1700444464
1700444465
List<String>subList=list.subList(0,2);
1700444466
1700444467
//设置列表为只读状态
1700444468
1700444469
list=Collections.unmodifableList(list);
1700444470
1700444471
//对list进行只读操作
1700444472
1700444473
doReadSomething(list)
1700444474
1700444475
//对subList进行读写操作
1700444476
1700444477
doReadAndWriteSomething(subList)
1700444478
1700444479
}
1700444480
1700444481
这在团队编码中特别有用,比如我生成了一个List,需要调用其他同事写的共享方法,但是有一些元素是不能修改的,想想看,此时subList方法和unmodifiableList配合着使用是不是就可以解决我们的问题了呢?防御式编程就是教我们如此做的。
1700444482
1700444483
这里还有一个问题,数据库的一张表可以有很多视图,我们的List也可以有多个视图,也就是可以有多个子列表,但问题是只要生成的子列表多于一个,则任何一个子列表就都不能修改了,否则就会抛出ConcurrentModificationException异常。
1700444484
1700444485
注意 subList生成子列表后,保持原列表的只读状态。
1700444486
1700444487
1700444488
1700444489
[
上一页 ]
[ :1.70044444e+09 ]
[
下一页 ]