三种获取字节码对象的方法,获取的都是同一个,因为保存的对象只有一个
Student s = new Student();
Class c1 = Student.class;
Class c2 =s.getClass();
Class c3 = Class.forName("com.test.reflector.Student");
重点是第三种获取对象的方法
例子的隐藏条件: 有一个Student类,构造方法 public Student(); private Student(String name); public Student(String name,int age); 成员变量 public String name ; private int age;有get和set方法
public class Student { private String name; public int age; public Student() { super(); // TODO Auto-generated constructor stub } public Student(String name, int age) { super(); this.name = name; this.age = age; } private Student(String name) { super(); this.name = name; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "Student [name=" + name + ", age=" + age + "]"; } public void play() { System.out.println("play"); } public void play(String str) { System.out.println("play--"+str); } }
注意:类反射能获取公有的构造方法 如果想要获取到私有的构造方法,就要使用getDeclaredConstructor,如果需要使用私有的构造方法,就要使用暴力访问constructor.setAccessible(true);
关于有参构造方法里面的参数列表怎么填,如果是字符串就String.class 如果是int型就用 int.class
Class c3 = Class.forName("com.test.reflector.Student"); //相当于获取到学生类
创建对象 Student stu = (Student) c3.newInstance(); //获取一个学生对象
获取字节码对象的无参构造 Constructor constructor = c3.getConstructor(); Student s = (Student)constructor.newInstance();
获取字节码对象的有参构造 Constructor constructor = c3.getConstructor(String.class,int.class); Student s = (Student)constructor.newInstance("张三",“11”);
获取所有公有的构造方法 Constructor[] constructors = c3.getConstructors();
获取所有包括私有的构造方法 Constructor[] constructors = c3.getDeclaredConstructors();
通过暴力访问使用私有构造方法
Constructor constructor = c3.getDeclaredConstructor(String.class);
constructor.setAccessible(true); //设置暴力访问
Student s= (Student) constructor.newInstance("aaa"); //不设置暴力访问,编译不会出错,运行会报错
java.lang.IllegalAccessException: Class com.reflector.Demo01 can not access a member of class com.woniuxy.reflector.Student with modifiers "private"
为公有成员赋值
1 Class c1 = Class.forName("com.reflector.Student"); 2 Student s= (Student) c1.newInstance(); 3 Field fieldAge = c1.getField("age"); 4 //给学生对象s的age字段赋值位11 5 fieldAge.set(s, 11); //参数列表(对象,要赋的值)
为私有成员赋值
1 Student s= (Student) c1.newInstance(); 2 Field fieldName = c1.getDeclaredField("name"); 3 fieldName.setAccessible(true); 4 //给学生对象s的私有字段name赋值 5 fieldName.set(s, "aaa"); 6 System.out.println(s);
调用无参方法
1 Class c1 = Class.forName("com.reflector.Student"); 2 Student s= (Student) c1.newInstance(); 3 Method method = c1.getMethod("play"); //调用学生的无参方法play 4 method.invoke(s); //输出这个对象的方法结果
调用有参方法
1 Class c1 = Class.forName("com.reflector.Student"); 2 Student s= (Student) c1.newInstance(); 3 Method method = c1.getMethod("play", String.class); 4 method.invoke(s, "aaa"); //要使用的对象 ,传递的参数