反射怎么来的:
写个例子:1、先写一个StudentDemo类:
package com.weizhaoyang.Student;public class StudentDemo{private String username;private Integer age;private String sex;public String getUsername() {return username;}public void setUsername(String username) {this.username = username;}public Integer getAge() {return age;}public void setAge(Integer age) {this.age = age;}public String getSex() {return sex;}public void setSex(String sex) {this.sex = sex;}}
2、在创建一个TestStudent的类,当我们创建好两个类的时候:编辑器软件就已经编译成了.class文件,不去运行也会编译成.class文件,因为编辑器里面配置了jdk。
package com.weizhaoyang.Student;public class TestStudent {}
在eclipse这里勾上自动编译了。
3、创建StudentDemo的实例:当new的过程中,也就是运行期间,把上面的.class文件加载到java虚拟机上面,并且会得到一个Student类对应的类对象。
package com.weizhaoyang.Student;public class TestStudent {public static void main(String[] args) {StudentDemo stu=new StudentDemo();}}
获取下类对象:这个student就是类对象。
//这个方法是Object中的方法Class student=stu.getClass();
说下怎么判断.class文件被加载到java虚拟机上?通过在一个类上加上静态块。
这个静态块执行:这个StudentDemo.class文件首次被加载到java虚拟机上才会执行。
再次运行下主函数:运行的结果如下,这时这个类文件就被加载到了jvm上了。在运行的时候就相当于用java命令执行类文件。java运行期才会把.class文件加载到jvm上运行。
当我们不去new的时候,也会拿到类对象的,类对象也就是Class对象 。
这个类对象是由java虚拟机第一次加载字节码class文件的时候就自动的把这个对象创建了起来。
代码如下:
再证实下这个事实:代码如下,说明还没有new的时候这个类对象就已经加载到内存里面去了。class文件只是用的时候才会加载。new的时候才会分配内存。
总结:下面的图就是当一个类的主函数被压栈的时候,就可以拿到当前类的Class对象,从而把Student.class加载到jvm上,从而在内存中分配一块内存用来存储Class对象 ,而这个Class对象就可以获取到类里的成员变量,方法,和构造函数。
获取到类对象之后是不能操作类成员的,必须通过反射来操作,代码如下:
总结:平常是通过类的实例获取类的信息,而反射是通过类对象类获取类信息。
私有的方法通过反射的外部类来也可以去调用它。但是可以用匿名内部来保护类的安全。