线程安全的AtomicLong使用

atomiclong 可以理解是加了synchronized的long。

public class Counter {  
    private static long counter = 0;  
    public static long addOne(){  
        return ++counter;  
    }  
} 

这个类在多线程的环境下就会有问题了,假如开多个线程都来使用这个计数类,它会表现的“不稳定”

    public static void main(String[] args) {  
        for(int i=0;i<100;i++){  
            Thread thread = new Thread(){  
                @Override  
                public void run() {  
                    try {  
                        Thread.sleep(100);  
                        if(Counter.addOne() == 100){  
                            System.out.println("counter = 100");  
                        }  
                    } catch (InterruptedException e) {  
                        e.printStackTrace();  
                    }  
                }  
            };  
            thread.start();  
        }  
    }  

程序会开100个线程,每个线程都会把counter 加一。那么应该有一个线程拿到counter =100的值,但实际运行情况是大多数据情况下拿不到100,在少数情况能拿到100.

因为 Counter 类在 addOne()方法被调用时,并不能保证线程的安全,即它不是原子级别的运行性,而是分多个步骤的。

打个比方:线程1首先取到counter 值,比如为10,然后它准备加1,这时候被线程2占用了cpu,它取到counter为10,然后加了1,得到了11。这时线程1 又拿到了CPU资源,继续它的步骤,加1为11,然后也得到了11。这就有问题了。

那么怎么解决它呢?JDK在concurrent包里提供了一些线程安全的基本数据类型的实现,比如 Long型对应的concurrent包的类是AtomicLong。

现在修改下代码:

    import java.util.concurrent.atomic.AtomicLong;  


    public class Counter {  
        private static AtomicLong counter = new AtomicLong(0);  


        public static long addOne() {  
            return counter.incrementAndGet();  
        }  
    }  

运行了多次,结果都是能输出counter = 100。

所以在多线程环境下,可以简单使用AtomicXXX 使代码变得线程安全。

转载出处:http://blog.csdn.net/yaqingwa/article/details/17737771

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值