UnSafe类中的一些重要方法
UnSafe类中的一些重要方法
JDK中的rt.jar保重Unsafe类中提供了硬件级别的原子性操作,Unsafe类中的方法都是navtice方法,他们使用JNI的方式访问C++实现库,下面我们来了解一下Unsafe提供的几个主要方法以及编程时如何使用Unsafe类做一些事情。
long objectFieldOffset(Field field)
方法;返回指定变量所属类中的内存偏移量,该偏移量仅在使用该Unsafe函数中访问指定字节时使用。如下代码使用Unsafe获取变量value在AtomicLong对象中的内存偏移。
static{
try{
valueOffset=unsafe.objectFieldOffset(AtomicLong.class.getDeclaredField("value"));
}catch(Exception e){
throw new Error(r);
}
}
int arrayBaseOffset(Class arrayClass)
方法:获取数组中第一个元素的地址
int arrayIndexScale(Class arrayClass)
方法:获取数组中一个元素的大小
boolean compareAndSwapLong(Object obj,long offset,long expect,long update)
方法比较对象obj中val值是否等于expect值如果相等就将其设置为update;
public native long getLongvolatile(Object obj,long offset)
方法:获取一个long值的属性
void putLongvolatile(Object obj,long offset,long value)
方法:设置obj对象中offset偏移地址对用的long类field值为value。
void putOrderedLong(Object obj,long offset,long value)
方法:
void park(boolean isAbsoulte,long time)
方法:阻塞当前线程(这个方法在AQS中的使对象等待时会使用到)。isAbsoulte
的为是否是绝对时间,如果isAbsoulte
为false,其中time为大于0,那么
当前线程会在等待time后唤醒。如果isAbsolute
为false,其中time为0,那么线程为无限等待。如果isAbosult
为true,那么time就是指的是绝对时间也就是换算为ms后的绝对时间。另外,当其他线程调用了当前阻塞线程的interrupt方法而中断了当前线程时,当前线程也会返回,而其他线程调用unPark
方法并且把当前线程作为参数时也会返回
void unpark(Object thread)
方法:唤醒调用park线程的线程
long getAndSetLong(Object obj,long offset,long update)
方法:获取对象obj中偏移量为offset的变量volatile予以的当前值,并设置变量volatile语义的值为update;
public final long getAndSetLong(Object obj,long offset , long update){
long l;
do{
l = getLongVolatile(obj,offset);
}while(!compareAndSwapLong(obj,offset,l,update));
return l;
}
long getAndAddLong(Object obj,long offset,long add)
方法:设置原始值为val+add;
public final long getAndSetLong(Object obj,long offset , long add){
long l;
do{
l = getLongVolatile(obj,offset);
}while(!compareAndSwapLong(obj,offset,l,l+add));
return l;
}