上一篇:反射调用成员 | 带你学《Java语言高级特性》之八十七
【本节目标】
本节介绍了绕过JVM的相关的对象管理机制实例化对象的Unsafe工具类,巩固加深对反射的理解。
Unsafe工具类
反射是Java的第一大特点,一旦打开反射的大门就可以有更加丰富的类设计形式。除了JVM本身支持的反射处理之外,在Java中也提供了一个Unsafe类(不安全的操作),这个类的主要特点是可以利用反射来获取对象,并且直接使用底层的C++来代替JVM执行,即:可以绕过JVM的相关的对象管理机制,一旦使用Unsafe,那么项目之中将无法继续使用JVM的内存管理机制以及垃圾回收处理。
但是如果要想使用Unsafe类首先就需要确认一下这个类中定义的构造方法与常量问题:
- 构造方法:
private Unsafe() {}
- 私有常量:
private static final Unsafe theUnsafe = new Unsafe()
但是需要注意的是,在这个Unsafe类中并没有提供static的方法,即:不能通过类似于传统的单例设计模式中提供的样式来进行操作,如果想要获得这个类的对象,就必须利用反射机制来完成。
import sun.misc.Unsafe;
import java.lang.reflect.Field;
public class JavaAPIDemo {
public static void main(String[] args) throws Exception {
Field field = Unsafe.class.getDeclaredField("theUnsafe");
field.setAccessible(true); // 解除封装处理
Unsafe unsafeObject = (Unsafe) field.get(null); // static属性不需要传递实例化对象
}
}
在传统的开发中,一个程序类必须要通过实例化对象后才可以调用类中的普通方法,尤其是以单例设计模式为例。
范例:使用Unsafe类绕过实例化对象的管理
import sun.misc.Unsafe;
import java.lang.reflect.Field;
public class JavaAPIDemo {
public static void main(String[] args) throws Exception {
Field field = Unsafe.class.getDeclaredField("theUnsafe");
field.setAccessible(true);
Unsafe unsafeObject = (Unsafe) field.get(null);
// 利用Unsafe类绕过了JVM管理机制,可以在没有实例化对象的情况下获取一个Singleton类实例化对象
Singleton instance = (Singleton) unsafeObject.allocateInstance(Singleton.class);
instance.print(); // www.mldn.cn
}
}
class Singleton{
private Singleton() {
System.out.println("*****Singleton类构造******")
}
public void print(){
System.out.println("www.mldn.cn");
}
}
Unsafe只能说为开发提供了一些更加方便的处理机制,但是这种操作由于不受JVM的管理,所以如果不是必须的情况下不建议使用。讲解这个类的主要目的是帮助大家巩固对于反射的理解。
想学习更多的Java的课程吗?从小白到大神,从入门到精通,更多精彩不容错过!免费为您提供更多的学习资源。
本内容视频来源于阿里云大学