原子更新字段类
如果我们只需要某个类里的某个字段,那么就需要使用原子更新字段类,Atomic包提供了以下三个类:
- AtomicIntegerFieldUpdater:原子更新整型的字段的更新器。
- AtomicLongFieldUpdater:原子更新长整型字段的更新器。
原子更新字段类都是抽象类,每次使用都时候必须使用静态方法newUpdater创建一个更新器。原子更新类的字段的必须使用public volatile修饰符。AtomicIntegerFieldUpdater的例子代码如下:
p
并发之AtomicIntegerFieldUpdater
基于反射的实用工具,可以对指定类的指定 volatile int 字段进行原子更新。此类用于原子数据结构,该结构中同一节点的几个字段都独立受原子更新控制。
先来看一段代码:
package automic; import java.util.concurrent.atomic.AtomicIntegerFieldUpdater; /** * 原子整型字段更新操作 * @author gosaint * */ public class AtomicIntegerFieldUpdaterTest { private static Class<Person> cls; /** * AtomicIntegerFieldUpdater说明 * 基于反射的实用工具,可以对指定类的指定 volatile int 字段进行原子更新。此类用于原子数据结构, * 该结构中同一节点的几个字段都独立受原子更新控制。 * 注意,此类中 compareAndSet 方法的保证弱于其他原子类中该方法的保证。 * 因为此类不能确保所有使用的字段都适合于原子访问目的,所以对于相同更新器上的 compareAndSet 和 set 的其他调用, * 它仅可以保证原子性和可变语义。 * @param args */ public static void main(String[] args) { // 新建AtomicLongFieldUpdater对象,传递参数是“class对象”和“long类型在类中对应的名称” AtomicIntegerFieldUpdater<Person> mAtoLong = AtomicIntegerFieldUpdater.newUpdater(Person.class, "id"); Person person = new Person(12345); mAtoLong.compareAndSet(person, 12345, 1000); System.out.println("id="+person.getId()); } }
package automic; class Person { volatile int id; public Person(int id) { this.id = id; } public void setId(int id) { this.id = id; } public int getId() { return id; } }
1)在上述的例子中,对于字段ID的修改,其中id的修饰必须是基本类型数据,用volatile修饰,不能是包装类型,int,long就可以,但是不可以是Integer和Long;
2) 必须是实例变量,不可以是类变量;
3) 必须是可变的变量,不能是final修饰的变量