sun.misc.Unsafe

package com.rt.sun.misc.utils;

public class Person {

    private static String staticStringField;

    private String stringField;

    private int intField;

    private long longField;

    public static String getStaticStringField() {
        return staticStringField;
    }

    public static void setStaticStringField(String staticStringField) {
        Person.staticStringField = staticStringField;
    }

    public String getStringField() {
        return stringField;
    }

    public void setStringField(String stringField) {
        this.stringField = stringField;
    }

    public int getIntField() {
        return intField;
    }

    public void setIntField(int intField) {
        this.intField = intField;
    }

    public long getLongField() {
        return longField;
    }

    public void setLongField(long longField) {
        this.longField = longField;
    }

    @Override
    public String toString() {
        return "Person{" +
                "staticStringField='" + staticStringField + "'" +
                "stringField='" + stringField + "'" +
                ", intField=" + intField +
                ", longField=" + longField +
                '}';
    }
}

 

package com.rt.sun.misc.utils;

import java.lang.reflect.Field;
import sun.misc.Unsafe;

public class UnsafeUtil {

    private static final Unsafe unsafe;

    static {
        unsafe = getUnsafeInstance();
    }


    public static void main(String[] args) {

        long staticStringFieldOffset = getStaticFieldOffset(Person.class, "staticStringField");
        System.out.println("类变量[staticStringField]相对于类内存地址的偏移量:"+staticStringFieldOffset);
        long stringFieldOffset = getFieldOffset(Person.class, "stringField");
        System.out.println("成员变量[stringField]相对于实例对象内存地址的偏移量:"+stringFieldOffset);
        long intFieldOffset =  getFieldOffset(Person.class, "intField");
        System.out.println("成员变量[intField]相对于实例对象内存地址的偏移量:"+intFieldOffset);
        long longFieldOffset =  getFieldOffset(Person.class, "longField");
        System.out.println("成员变量[longField]相对于实例对象内存地址的偏移量:"+longFieldOffset);

        Person person = new Person();
        System.out.println("初始:"+person.toString());
        // Person.staticStringFieldOffset="staticStringField-value";
        putObject(Person.class, staticStringFieldOffset, "staticStringField-value");
        // person.stringFieldOffset="stringField-value";
        putObject(person, stringFieldOffset, "stringField-value");
        // person.intFieldOffset=1;
        putInt(person, intFieldOffset, 1);
        // person.longFieldOffset=1L;
        putLong(person, longFieldOffset, 1L);
        System.out.println("修改之后:"+person.toString());

        // [CAS]Person.staticStringFieldOffset="cas-staticStringField-value";
        compareAndSwapObject(person, staticStringFieldOffset, person.getStringField(), "cas-staticStringField-value");
        // [CAS]person.stringFieldOffset="cas-stringField-value";
        compareAndSwapObject(person, stringFieldOffset, person.getStringField(), "cas-stringField-value");
        // [CAS]person.intFieldOffset=2;
        compareAndSwapInt(person, intFieldOffset, person.getIntField(), 2);
        // [CAS]person.longFieldOffset=2L;
        compareAndSwapLong(person, longFieldOffset, person.getLongField(), 2L);
        System.out.println("CAS修改之后:"+person.toString());
    }


    /**
     * 通过反射创建Unsafe实例对象
     * @return
     */
    public static Unsafe getUnsafeInstance() {
        Unsafe unsafe = null;
        try {
            Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe");
            theUnsafe.setAccessible(true);
            unsafe = (Unsafe) theUnsafe.get(null);
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e1) {
            e1.printStackTrace();
        }
        return unsafe;
    }

    /**
     * 获取某类的静态变量相对于类内存地址的偏移量
     * @param cls           类
     * @param fieldName     类的静态变量名
     * @return              静态变量相对于类内存地址的偏移量
     */
    public static long getStaticFieldOffset(Class<?> cls, String fieldName) {
        long offset = 0L;
        try {
            offset = unsafe.staticFieldOffset(cls.getDeclaredField(fieldName));
        } catch (NoSuchFieldException e0) {
            e0.printStackTrace();
        }
        return offset;
    }

    /**
     * 获取类的成员变量相对于实例对象内存地址的偏移量
     * @param cls           类
     * @param fieldName     实例对象中的成员变量名
     * @return              成员变量相对于实例对象内存地址的偏移量
     */
    public static long getFieldOffset(Class<?> cls, String fieldName) {
        long offset = 0L;
        try {
            offset = unsafe.objectFieldOffset(cls.getDeclaredField(fieldName));
        } catch (NoSuchFieldException e0) {
            e0.printStackTrace();
        }
        return offset;
    }

    /**
     * 修改类的静态变量值
     * @param cls               类
     * @param fieldOffset       类变量相对于类内存地址的偏移量
     * @param fieldValue        静态变量的新值
     */
    public static void putObject(Class<?> cls, long fieldOffset, String fieldValue) {
        unsafe.putObject(cls, fieldOffset, fieldValue);
    }

    /**
     * 修改对象的成员变量值
     * @param person            对象实例
     * @param fieldOffset       成员变量相对于实例对象内存地址的偏移量
     * @param fieldValue        成员变量的新值
     */
    public static void putObject(Person person, long fieldOffset, String fieldValue) {
        unsafe.putObject(person, fieldOffset, fieldValue);
    }

    /**
     * 修改对象的成员变量值
     * @param person            对象实例
     * @param fieldOffset       成员变量相对于实例对象内存地址的偏移量
     * @param fieldValue        成员变量的新值
     */
    public static void putInt(Person person, long fieldOffset, int fieldValue) {
        unsafe.putInt(person, fieldOffset, fieldValue);
    }

    /**
     * 修改对象的成员变量值
     * @param person            对象实例
     * @param fieldOffset       成员变量相对于实例对象内存地址的偏移量
     * @param fieldValue        成员变量的新值
     */
    public static void putLong(Person person, long fieldOffset, long fieldValue) {
        unsafe.putLong(person, fieldOffset, fieldValue);
    }

    /**
     * CAS操作更新值
     * @param person        修改的对象
     * @param fieldOffset   对象的成员变量相对于对象内存地址的偏移量
     * @param expect        期望值
     * @param value         更新的值
     */
    public static void compareAndSwapObject(Person person, long fieldOffset, Object expect, Object value) {
        unsafe.compareAndSwapObject(person, fieldOffset, expect, value);
    }

    /**
     * CAS操作更新值
     * @param person        修改的对象
     * @param fieldOffset   对象的成员变量相对于对象内存地址的偏移量
     * @param expect        期望值
     * @param value         更新的值
     */
    public static void compareAndSwapInt(Person person, long fieldOffset, int expect, int value) {
        unsafe.compareAndSwapInt(person, fieldOffset, expect, value);
    }

    /**
     * CAS操作更新值
     * @param person        修改的对象
     * @param fieldOffset   对象的成员变量相对于对象内存地址的偏移量
     * @param expect        期望值
     * @param value         更新的值
     */
    public static void compareAndSwapLong(Person person, long fieldOffset, long expect, long value) {
        unsafe.compareAndSwapLong(person, fieldOffset, expect, value);
    }

    /**
     * 将当前线程挂起
     * @param abs       abs==false,表示timeout的时间单位是纳秒
     *                  abs==false && timeout==0 表示线程将一直挂起,直至被恢复或被中断
     * @param timeout   挂起的时间
     */
    public static void park(boolean abs, long timeout) {
        unsafe.park(abs, timeout);
    }

    /**
     * 恢复被挂起的线程
     * @param thread    线程对象
     */
    public static void unpark(Thread thread) {
        unsafe.unpark(thread);
    }


}

执行main方法,结果如下:

类变量[staticStringField]相对于类内存地址的偏移量:104
成员变量[stringField]相对于实例对象内存地址的偏移量:24
成员变量[intField]相对于实例对象内存地址的偏移量:12
成员变量[longField]相对于实例对象内存地址的偏移量:16
初始:Person{staticStringField='null'stringField='null', intField=0, longField=0}
修改之后:Person{staticStringField='staticStringField-value'stringField='stringField-value', intField=1, longField=1}
CAS修改之后:Person{staticStringField='staticStringField-value'stringField='cas-stringField-value', intField=2, longField=2}

 

转载于:https://www.cnblogs.com/517cn/p/10909051.html

### 回答1: sun.misc.unsafe.park(native me) 是Java中的一个方法,它是用来阻塞当前线程的。具体来说,它会使当前线程进入等待状态,直到被唤醒或者被中断。这个方法通常用于实现线程的同步和互斥。 ### 回答2: sun.misc.unsafe.park(native me 是一个Java API中的方法,它通过使用Unsafe类的park方法来使当前线程进入休眠状态。在这个方法中,native关键字表示它是由本地代码实现的,也就是说具体的实现是由底层的操作系统提供的。 调用sun.misc.unsafe.park(native me 方法可以实现线程的等待和唤醒操作。当当前线程执行到这个方法时,会立即进入休眠状态,暂停自己的执行,直到其他线程通过调用Unsafe类的unpark方法唤醒它。 这个机制通常用于线程同步的场景,可以实现线程之间的协作。比如,一个生产者线程通过调用Unsafe类的park方法进入休眠状态,等待某个条件满足后再继续执行;而一个消费者线程在满足某个条件后,通过调用Unsafe类的unpark方法唤醒生产者线程,使其恢复执行。 需要注意的是,sun.misc.unsafe.park(native me 方法通常不建议直接使用,因为它是一个内部API,可能会在未来的版本中被移除或者修改。在实际应用中,可以使用更高级的并发工具,如Lock和Condition、CountDownLatch、Semaphore等来实现线程的等待和唤醒操作,这些API提供了更加安全和可靠的线程同步机制。 ### 回答3: sun.misc.unsafe.park(native me)是Java中的一个方法,它是由sun.misc.Unsafe类提供的。该方法主要用于线程的阻塞等待。 在Java中,线程可以通过调用park方法进入阻塞状态,直到某个条件满足或者其他线程唤醒它。park方法是一种低级的阻塞机制,它不会占用CPU资源,因此适用于一些需要较长等待时间的场景。 使用park方法时,我们需要传入一个native me参数。native me是指要阻塞的线程对象,也就是当前执行park方法的线程自身。 park方法可以通过其他线程的unpark方法来唤醒被阻塞的线程。unpark方法会给指定的线程一个许可证,使得park方法立即返回。 使用park方法进行线程的阻塞等待可以提高线程的效率和性能,避免了一直占用CPU资源。 需要注意的是,sun.misc.unsafe.park(native me)方法属于sun.misc包下的不稳定的、不建议直接使用的API。在实际开发中,应该尽量避免使用这些API,而是使用Java提供的高级并发类库,如java.util.concurrent包下的Locks和Conditions,或者使用更高层次的并发框架,如线程池。这些类库和框架提供了更稳定、易用且可扩展的线程同步和阻塞等待机制。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值