ArrayList线程安全问题以及解决方案

ArrayList在多线程环境下不是线程安全的,其add方法可能导致元素丢失或下标越界。问题主要出现在容量判断和元素添加这两个非原子操作上。解决线程安全问题可以使用synchronized同步方法或者切换到CopyOnWriteArrayList,后者通过读写分离和加锁确保并发安全性。
摘要由CSDN通过智能技术生成

ArrayList是否为线程安全的?

 ArrayList产生线程安全的原因是什么?

 ArrayList出现问题的方法为add方法,首先我们看下add方法的源码。

 public boolean add(E e) {
    ensureCapacityInternal(size + 1); 
    elementData[size++] = e;
    return true;
   }

可以看出add方法主要包含两个重要的操作:

1、判断集合容量是否还足够添加元素:此方法在多线程情况下会出现下标越界的问题,假如初始容量为5,线程A调用add方法,而elementData的容量为6,因此无需扩容。线程B同时调用add方法,而elementData的容量为6,因此也无需扩容,但是实际需要容量为7。

2、将元素添加到指定的位置:由于size++也是非原子操作,此方法可能出现线程B将线程Aadd位置的元素覆盖,而应该正确add的位置元素为null。

有什么方法能够解决上述的问题?

 1、在使用多线程add元素时使用synchronized方法,保证只有一个线程在执行add方法。

2、使用CopyOnWriteArrayList,该集合读写分离,在写数据时,使用lock锁控制并发,在读数据时分情况而定。

参考博客:CopyOnWriteArrayList集合

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值