dcLunatic's blog

Java中获得实例的方法

字数统计: 877阅读时长: 4 min
2018/09/21 Share

获取实例的方法

通过new关键字

通过new来获得一个类的实例,这是最最最常见的了。

通过clone方法

首先该类实现了Cloneable接口,实现了clone()方法,这时候,便可以通过调用某个已存在的对象的clone()方法来获得实例了。

1
2
3
4
5
6
7
8
9
10
11
12
13
public class Main throws Exception{
public static void main(String... args){
Test t1 = new Test();
Test t2 = t1.clone();
}
}
class Test implements Cloneable{
public Test(){}
@Override
public Object clone() throws CloneNotSupportedException{
return super.clone();
}
}

对于克隆的话,需要了解一下浅克隆跟深克隆。

通过调用Class下的newInstance()方法(只能无参构造)

在Class类下,有一个方法newInstance(),该方法可以在我们获取到一个类的Class对象后,通过该Class对象新建一个实例,但是在新建实例的时候,无法传递参数,也就是说,只能用于无参构造。

1
2
3
4
5
6
7
public class Main{
public static void main(String... args){
Test t1 = Test.class.newInstance();
Test t2 = t1.getClass().newInstance();
Test t2 = (Test)Class.forName("Test").newInstance();
}
}

这里的话,主要就是如何获取一个类的Class对象了,首先,直接通过.class访问即可,其次,通过类的getClass()方法获取,再者,也可以类似于数据库开发中经常用到的Class.forName(String)来获取。

在数据库开发中,我们会经常看到Class.forName()这个方法的调用,但是接下来就没有类似于上面的调用newInstance()方法了,但需要用到的实例却是存在了。

在这里,Class.forName()是用来动态加载类,在加载类的时候,自然就会加载了类里面的一些东西了,如果刚好这个类中有静态的初始化器的话,自然的,jvm就会执行。

在对应的源码中我们可以看到

1
2
3
4
5
6
7
8
9
10
11
12
public class Driver extends NonRegisteringDriver implements java.sql.Driver {
static {
try {
java.sql.DriverManager.registerDriver(new Driver());
} catch (SQLException E) {
throw new RuntimeException("Can't register driver!");
}
}
public Driver() throws SQLException {
// Required for Class.forName().newInstance()
}
}

自然的,也就有了。

通过Constructor类的newInstance()方法

和Class类的newInstance()方法很像,java.lang.reflect.Constructor类中也有一个newInstance()方法可以创建对象,通过反射来获得类的任何构造方法。

1
2
3
4
5
6
7
8
9
import java.lang.reflect.*;
public Class Main{
public static void main(String... args){
Constructor<Test> c = Test.class.getConstructor();
Test t1 = c.newInstance();
//如果Test类有这种构造方法的话
Test t2 = c.newInstance("arg1", "arg2");
}
}

通过反序列化

当我们将对象序列化成二进制字节码后,我们也可以将这个二进制字节码通过反序列化变成一个对象。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
import java.io.*;
public class Main implements Serializable{
public static void main(String[] args) {

System.out.println("Hello world");
SerializeDemo();
DeserializeDemo();

}
private static void SerializeDemo(){
try {
Test test = new Test("John", 15);
ObjectOutputStream oo = new ObjectOutputStream(new FileOutputStream(new File("/root/Desktop/test.txt")));
oo.writeObject(test);
System.out.println("序列化结束");
oo.close();
}catch(FileNotFoundException e){
System.out.println("无法读写文件");
}catch(IOException e){
System.out.println("IO异常");
}
}
private static void DeserializeDemo(){
try{
ObjectInputStream oi = new ObjectInputStream(new FileInputStream(new File("/root/Desktop/test.txt")));
Test test = (Test)oi.readObject();
System.out.println("反序列化成功");
System.out.println(test.toString());
}catch(Exception e){
e.printStackTrace();
}

}
}

class Test implements Serializable{
private static final long serialVersionUID = 1L;
private int age;
private String name;
private String sex;
public Test(String name, int age){
this.age = age;
this.name = name;
}
@Override
public String toString() {
return "Test{" +
"age=" + age +
", name='" + name + '\'' +
'}';
}
}
CATALOG
  1. 1. 获取实例的方法
    1. 1.1. 通过new关键字
    2. 1.2. 通过clone方法
    3. 1.3. 通过调用Class下的newInstance()方法(只能无参构造)
    4. 1.4. 通过Constructor类的newInstance()方法
    5. 1.5. 通过反序列化