Vector并非绝对线程安全

1.前言

Java集合框架中的Vector集合通过对可能引发线程安全问题的方法(例如:add()、remove()、size()等等)加synchronized关键字实现了线程安全,但这种实现仅能在一定程度上减少多线程并发操作下出现问题的可能性,例如下面的情况就可能会出现线程不安全问题。

Vector<String> vector = new Vector<>();

......
......

for(int i = 0; i < vector.size(); i++){

    //当前线程时间片到期,当前线程被挂起

    ...... //其他线程删除vector内的元素

    //当前线程再次获取到时间片,但vector内的元素已被其他线程删除,可能引发数组越界异常
    System.out.println(vector.get(i));
        

}

2.案例演示

基于以上的思路,可以通过以下代码来验证Vector的线程不安全问题

import java.util.Vector;


public class TestVectorNoSafe {

    private static Vector<Integer> vector = new Vector<>();

    public static void main(String[] args) {
        while (true) {
            for (int i = 0; i < 10; i++)
                vector.add(i);

            Thread removeThread = new Thread(new Runnable() {
                @Override
                public void run() {
                    for (int i = 0; i < vector.size(); i++) {
                        Thread.yield();
                        vector.remove(i);
                    }
                }
            });

            Thread printThread = new Thread(new Runnable() {
                @Override
                public void run() {
                    for (int i = 0; i < vector.size(); i++) {
                        Thread.yield();
                        System.out.println(vector.get(i));
                    }
                }
            });

            removeThread.start();
            printThread.start();

            while (Thread.activeCount() > 20) ;//防止线程太多计算机卡死
        }
    }
}

上面的代码运行后,就会出现数组越界异常

3.结论

Vector所谓的线程安全是指调用Vector类的成员方法时,其他线程不能再访问该Vector对象。但是在调用两个Vector成员方法时,当前线程有可能再完成第一个方法后时间片到期,这时其他线程可以访问该Vector对象,造成调用第二个成员方法的结果可能与预想结果不同。这时为保证线程安全,需要加synchronized。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值