package com.prac.thread;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;
/**
* 说明:使用循环CAS实现原子操作
*/
public class Counter {
private AtomicInteger atomicI = new AtomicInteger(0);
private int i = 0;
public static void main(String[] args) {
final Counter cas = new Counter();
List<Thread> ts = new ArrayList<Thread>();
long start = System.currentTimeMillis();
for(int j=0;j<10;j++){
Thread t = new Thread(new Runnable() {
@Override
public void run() {
for(int i=0;i<100;i++){
cas.count();
cas.safeCount();
}
}
});
ts.add(t);
}
for(Thread t:ts){
t.start();
}
//等待所有线程执行完成
for(Thread t :ts){
try {
t.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(cas.i);
System.out.println(cas.atomicI.get());
System.out.println(System.currentTimeMillis() - start);
/**
* 输入结果:
* 996
* 1000
* 2
* 产生结果不一致的原因是 :多个处理器同时从各自缓存中读取变量i,比如此时i=5,各自+1后放入内存,
* 如果保证操作是原子的,就必须一个时刻只能有一个处理器在处理,即一个线程在操作。
*
*/
}
/**
* 使用CAS实现线程安全计数器
*/
private void safeCount(){
for(;;){
int i = atomicI.get();
//compareAndSet方法简介:如果当前值==为期望值,则将该值原子设置为给定的更新值
//即atomicI = i,那么将atomicI 设置为 i+1;
boolean suc = atomicI.compareAndSet(i, ++i);
if(suc){
break;
}
}
}
/**
* 非线程安全计数器
*/
private void count(){
i++;
}
}
使用循环CAS实现原子操作
最新推荐文章于 2024-02-25 11:19:53 发布