前三者都借助了构造函数。
一、new调用有参、无参构造函数创建对象。
二、反射 1、Class.newInstance()借助Class类的方法创建,将调用无参构造函数创建对象。
Student stu = (Student)Class.forName("pers.xxx.entity.Student").newInstance();
// 或者
Student stu = Student.class.newInstance();
2、Constructor.newInstance()
来自java.lang.reflect.Constructor类。可以调用有参、无参和私有的构造函数。
其实第二种方式内部还是调用了这种。
Constructor三、Cloneable.clone()constructor = Student.class.getConstructor(); Student stu = constructor.newInstance();
调用clone()方法(浅拷贝),JVM就会创建一个新对象并返回新对象地址,把可以复制的内容都分配内存创建一份新的,不能的就把地址传过去。
这种方式不会调用构造函数。
首先要实现Cloneable这个空接口。
Student stu1 = (Student)stu.clone();四、反序列化
反序列化时,JVM就会创建对象,而且不调用构造函数。
首先要实现Serializable接口。
ObjectInputStream in = new ObjectInputStream(new FileInputStream("data.obj"));
Student str = (Student)in.readObject();
五、Unsafe.allocateInstance()
直接操作内存,不用构造器。
new方式没办法用在私有构造函数。
那直接把安全检查ban掉怎么样?
安全检查机制默认是开启的,所以private的东西都被禁止访问。
怎么关闭?
setAccessible(true),这样就可以访问private的东西了。
try{
Constructor constructor = Thing.class.getConstructor();
constructor.setAccessible(true);
}catch(NoSuchMethodException e){
e.printStackTrace();
}
Constructorconstructor1 = Unsafe.class.getConstructor(); // 通过构造器 Unsafe unsafe = constructor1.newInstance(); // 通过字段 Field field = Unsafe.class.getDeclaredField("theUnsafe"); field.setAccessible(true); Unsafe unsafe1 = (Unsafe) field.get(null); // 创建实例 Thing thing = (Thing) unsafe.allocateInstance(Thing.class); Thing thing1 = (Thing) unsafe1.allocateInstance(Thing.class);



