longaccumulator 是 java 8 提供的灵活并发累加器,支持自定义聚合函数(如 max/min/xor)和单位元,满足结合律与交换律即可;其构造需 longbinaryoperator 和 identity 参数,可无缝替代 longadder 并扩展功能。

LongAccumulator 是 Java 8 引入的并发工具类,适用于需要自定义聚合逻辑(如取最大值、最小值、异或、幂运算等)的多线程场景;而 LongAdder 仅支持加法累加,灵活性有限。关键在于:用 LongAccumulator 替代 LongAdder 并不增加复杂度,只需传入一个二元操作函数和初始值。
理解 LongAccumulator 的核心参数
构造 LongAccumulator 需要两个关键参数:
-
LongBinaryOperator accumulatorFunction:定义“当前值”与“新输入值”如何合并,例如
(a, b) -> Math.max(a, b)表示求最大值 -
long identity:恒等元(单位元),即满足
f(identity, x) == x的初始值,例如 max 对应Long.MIN_VALUE,min 对应Long.MAX_VALUE,异或对应0L
注意:该函数必须满足结合律和交换律(JDK 文档明确要求),否则结果不可靠。例如 (a,b)->a-b 不满足结合律,禁止使用。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
常用聚合模式的写法示例
以下均为线程安全、无锁、高性能的写法:
-
求最大值:
new LongAccumulator(Math::max, Long.MIN_VALUE) -
求最小值:
new LongAccumulator(Math::min, Long.MAX_VALUE) -
按位异或(XOR):
new LongAccumulator((a, b) -> a ^ b, 0L) -
乘积(需谨慎溢出):
new LongAccumulator(Math::multiplyExact, 1L)(推荐配合 try-catch 或使用 BigInteger 变体)
正确调用 accumulate() 与 get() 的时机
accumulate(x) 是核心更新方法,它原子地将 x 按指定规则合并进内部状态;get() 返回当前近似聚合结果(最终一致,非强实时):
- 多个线程可并发调用
accumulate(),无需同步 - 不要在循环中频繁调用
get()做条件判断(如 while(get() - 若需最终精确值,直接调用
get()即可;它不会阻塞,且比sumThenReset()更轻量(后者会清零)
与 LongAdder 的兼容性与迁移技巧
LongAdder 本质是 LongAccumulator 的特例:new LongAccumulator((a,b)->a+b, 0L)。因此:
- 已有 LongAdder 代码可无缝替换为 LongAccumulator,只需调整构造参数
- 若后续业务扩展需要支持 min/max 等,无需重构并发结构,只需换函数和 identity
- 两者都基于分段累加 + Striped64 机制,性能相当,内存开销接近
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










