DoubleAccumulator、LongAccumulator、DoubleAdder、LongAdder是JDK1.8新增的部分,是对AtomicLong等类的改进。比如LongAccumulator与LongAdder在高并发环境下比AtomicLong更高效。本文以LongAdder为例,学习这些类。
API中是这么介绍的:LongAdder中会维护一组(一个或多个)变量,这些变量加起来就是要以原子方式更新的long型变量。当更新方法add(long)在线程间竞争时,该组变量可以动态增长以减缓竞争。方法sum()返回当前在维持总和的变量上的总和。与AtomicLong相比,LongAdder更多地用于收集统计数据,而不是细粒度的同步控制。在低并发环境下,两者性能很相似。但在高并发环境下,LongAdder有着明显更高的吞吐量,但是有着更高的空间复杂度。
outline
//构造函数
LongAdder()
//创建初始和为零的新加法器。
//方法摘要
void add(long x)
//添加给定的值。
void decrement()
//相当于add(-1)。
double doubleValue()
//在扩展原始转换之后返回sum()as double。
float floatValue()
//在扩展原始转换之后返回sum()as float。
void increment()
//相当于add(1)。
int intValue()
//返回sum()作为int一个基本收缩转换之后。
long longValue()
//相当于sum()。
void reset()
//重置将总和保持为零的变量。
long sum()
//返回当前的总和。
long sumThenReset()
//等同于sum()后面的效果reset()。
String toString()
//返回。的字符串表示形式sum()。
例1:使用LongAdder实现long型变量的原子访问和更新
在Java并发编程札记-(三)JUC原子类-02原子方式更新单个变量一文中,例1:long型变量的原子访问和更新使用了AtomicLong实现了原子方式更新long型变量,本文对例子稍作修改。
将计数器类Counter修改为如下
class Counter {
private static LongAdder counter = new LongAdder();
public static long addOne() {
counter.add(1);
return counter.sum();
}
}
数次运行例1:long型变量的原子访问和更新中的测试程序,,发现结果全部为计数器值最终值为100。说明说明次计数器在多线程环境下可用,LongAdder实现long型变量的原子访问和更新。
实现原理
与其他原子类一样,LongAdder也是基于CAS实现的。
LongAdder可以代替AtomicLong吗
当然不能。在上面已经提到,与AtomicLong相比,LongAdder更多地用于收集统计数据,而不是细粒度的同步控制。而且,LongAdder只提供了add(long)和decrement()方法,想要使用cas方法还是要选择AtomicLong。
DoubleAdder、LongAccumulator、DoubleAccumulator与LongAdder很相似,就不多做介绍了。
本文就讲到这里,想了解Java并发编程更多内容请参考:
- Java并发编程札记-目录
END.