简单介绍
AtomicIntegerArray是Integer数组的线程安全原子类,和他类似的还有AtomicLongArray,AtomicReferenceArray,从实现上来说这三个都差不多,因此这里我们仅对AtomicIntegerArray进行分析。同样的,AtomicIntegerArray底层使用unsafe进行对数据的操作。
重要字段
private static final Unsafe unsafe = Unsafe.getUnsafe();
// 获取数组起始位置的偏移量
private static final int base = unsafe.arrayBaseOffset(int[].class);
private static final int shift;
private final int[] array;
static {
// 获取数据元素的大小(size),int类型的是 4
int scale = unsafe.arrayIndexScale(int[].class);
if ((scale & (scale - 1)) != 0)
throw new Error("data type scale not a power of two");
// int类型(4)的前置0个数为29
// 表达式返回位移量,用于计算下标。用于<<操作符,表示乘以2^shift 2^2=4
shift = 31 - Integer.numberOfLeadingZeros(scale);
}
构造函数
public AtomicIntegerArray(int length) {
array = new int[length];
}
public AtomicIntegerArray(int[] array) {
// Visibility guaranteed by final field guarantees
this.array = array.clone();
}
AtomicIntegerArray的构造函数很简单,就是初始化了一个数组。
重要方法
unsafe.getAndAddInt
// i位置加一,返回i位置旧值
public final int getAndIncrement(int i) {
return getAndAdd(i, 1);
}
// i位置减一,返回i位置旧值
public final int getAndDecrement(int i) {
return getAndAdd(i, -1);
}
// i位置加delta,返回i位置旧值
public final int getAndAdd(int i, int delta) {
return unsafe.getAndAddInt(array, checkedByteOffset(i), delta);
}
// i位置加一,返回i位置新值
public final int incrementAndGet(int i) {
return getAndAdd(i, 1) + 1;
}
// i位置减一,返回i位置新值
public final int decrementAndGet(int i) {
return getAndAdd(i, -1) - 1;
}
// i位置加delta,返回i位置新值
public final int addAndGet(int i, int delta) {
return getAndAdd(i, delta) + delta;
}
unsafe.compareAndSwapInt
// 不保证有序性的原子方法
public final boolean weakCompareAndSet(int i, int expect, int update) {
return compareAndSet(i, expect, update);
}
// i位置使用expect比较,匹配则更新为update,成功返回true
public final boolean compareAndSet(int i, int expect, int update) {
return compareAndSetRaw(checkedByteOffset(i), expect, update);
}
// i位置使用expect比较,匹配则更新为update,成功返回true
private boolean compareAndSetRaw(long offset, int expect, int update) {
return unsafe.compareAndSwapInt(array, offset, expect, update);
}
get/set
// 从i位置获得数据
public final int get(int i) {
return getRaw(checkedByteOffset(i));
}
// 从offset位置获得数据
private int getRaw(long offset) {
return unsafe.getIntVolatile(array, offset);
}
// i位置赋值newValue
public final void set(int i, int newValue) {
unsafe.putIntVolatile(array, checkedByteOffset(i), newValue);
}
// i位置赋值newValue,仅在get的时候才真正同步到主内存
public final void lazySet(int i, int newValue) {
unsafe.putOrderedInt(array, checkedByteOffset(i), newValue);
}
// i位置赋值newValue
public final int getAndSet(int i, int newValue) {
return unsafe.getAndSetInt(array, checkedByteOffset(i), newValue);
}
总结
AtomicIntegerArray是对数组的线程安全封装,提供对数组某个位置的原子操作,底层依旧使用Unsafe类进行操作。