什么是反射?
Java安全可以从反序列化漏洞说起,反序列化漏洞又可以从反射说起。反射是⼤多数语⾔⾥都必不可少的组成部分,对象可以通过反射获取他的类,类可以通过反射拿到所有⽅法(包括私有),拿到的⽅法可以调⽤,总之通过“反射”,我们可以将Java这种静态语⾔附加上动态特性。可能说完这一两句话大家还是不知道反射是个啥玩意,现在为了让大家容易理解,先为大家提出一个需求,通过这个需要来引出反射。需求如下:
根据配置文件re.properties指定信息,创建对象并调用方法。
classfullpath=com.lxflxf.Cat
method=hi
这样的需求在学习框架时很多, 即在通过外部文件配置,在不修改源码的情况下,来控制程序。
我们使用现有技术可以做到吗?咱们可以动手写一下。
首先创建配置文件,写入上述内容,然后创建一个类,写入如下内容:
public class Cat {
private String name = "小猫";
public void hi(){
System.out.println("hi" + name);
}
}
传统的方法是不是我们可以先new一个对象,然后再调用它的方法。写法如下:
Cat cat = new Cat();
cat.hi();
通过传统方法,确实可以调用hi()方法,但是这和我们的需求不一样,这里我们是要根据配置文件re.properties指定信息来完成。到了这里,有同学就说了,咱们可以通过IO流的方式来读取配置文件的信息。好,咱们用代码来写一下。
使用Properties来读写配置文件。案例代码如下:
Properties properties = new Properties();
properties.load(new FileInputStream("src//re.properties"));
String classfullpath = properties.get("classfullpath").toString();
String methodName = properties.get("method").toString();
System.out.println("classfullpath" + classfullpath);
System.out.println("methodName=" + methodName);
运行一下,发现成功读取到内容。
然后需要创建对象,怎么创建对象呢?有同学就说了,咱们可以直接 new classfullpath ,这样不就好了嘛?嗯,想法不错,下回不要想了。不要忘记了,我们现在的classfullpath可是字符串类型,怎么能去 new 呢。所以现有技术是做不到这个事情的。那么这里就要引入我们要讲的重点——反射机制。
为了能更好地理解反射,这里先写一个小案例,然后再去解释。
第一步、加载类