目录
1、2 第二组:java.lang.reflect.Field
1、3 第三组:java.lang.reflect.Mehtod
1、4 第四组:java.lang.reflect.Constructor
1、通过反射获取类的结构信息
1、1 第一组:java.lang.Class
1、getName:获取全类名
2、getSimpleName:获取简单类名
3、getFields:获取所有public修饰的属性 :包含本类的以及父类的
4、getDeclaredFields : 获取本类中的所有属性
5、getMethods 获取所有public修饰的方法 包含本类以及父类的
6、getDeclaredMethods: 获取本类中所有的方法
7、getConstructors: 获取所有的构造器,公共的
8、getDeclaredConstructors: 获取本类中所有构造器
9、getPackage: 以Package形式返回 包信息
10、getSuperClass :以class形式返回父类信息
11、getInterfaces: 以Class[] 形式返回接口信息
12、getAnnotations: 以Annotation[] 形式返回注解信息
测试代码
/**
* @description:第一组方法的api
*/
@Test
public void api_01() throws ClassNotFoundException {
//得到class对象
Class<?> personClass = Class.forName("com.demo.reflection.Person");
//1、getName:获取全类名
System.out.println(personClass.getName());//com.demo.reflection.Person
//2、getSimpleName:获取简单类名
System.out.println(personClass.getSimpleName());//Person
//3、getFields:获取所有public修饰的属性 :包含本类的以及父类的
Field[] fields = personClass.getFields();
Arrays.stream(fields).forEach(field -> System.out.println(field.getName()));//name hobby
//4、getDeclaredFields : 获取本类中的所有属性
Field[] declaredFields = personClass.getDeclaredFields();
Arrays.stream(declaredFields).forEach(declaredField -> {
System.out.println(declaredField.getName()); //name age job sal
});
//5、getMethods 获取所有public修饰的方法 包含本类以及父类的
Method[] methods = personClass.getMethods();
Arrays.stream(methods).forEach(method -> {
System.out.println(method.getName());
}); //m1 superm1 wait wait wait equals toString hashCode getClass notify notifyAll
//6、getDeclaredMethods: 获取本类中所有的方法
Method[] declaredMethods = personClass.getDeclaredMethods();
Arrays.stream(declaredMethods).forEach(declaredMethod -> {
System.out.println(declaredMethod.getName());//m1 m2 m4 m3
});
//7、getConstructors: 获取所有的构造器
Constructor<?>[] constructors = personClass.getConstructors();
Arrays.stream(constructors).forEach(constructor -> System.out.println(constructor.getName()));
//com.demo.reflection.Person
//com.demo.reflection.Person
//com.demo.reflection.Person
//8、getDeclaredConstructors: 获取本类中所有构造器
System.out.println("==============8==================");
Constructor<?>[] declaredConstructors = personClass.getDeclaredConstructors();
Arrays.stream(declaredConstructors).forEach(declaredConstructor -> {
System.out.println(declaredConstructor.getName());
});
//com.demo.reflection.Person
//com.demo.reflection.Person
//com.demo.reflection.Person
//com.demo.reflection.Person
//9、getPackage: 以Package形式返回 包信息
System.out.println("============9================");
System.out.println(personClass.getPackage().getName());
//com.demo.reflection
//10、getSuperClass :以class形式返回父类信息
System.out.println("=========10============");
System.out.println(personClass.getSuperclass().getName());
//com.demo.reflection.A
//11、getInterfaces: 以Class[] 形式返回接口信息
System.out.println("==============11============");
Class<?>[] interfaces = personClass.getInterfaces();
for (Class<?> anInterface : interfaces) {
System.out.println(anInterface.getName());
}
//com.demo.reflection.IA
//com.demo.reflection.IB
//12、getAnnotations: 以Annotation[] 形式返回注解信息
System.out.println("==============12============");
Annotation[] annotations = personClass.getAnnotations();
for (Annotation annotation : annotations) {
System.out.println(annotation);
}
//@java.lang.Deprecated()
}
}
实体
class A {
public String hobby;
public void superm1() {
}
public A(String hobby) {
this.hobby = hobby;
}
public A() {
}
}
interface IA {
}
interface IB {
}
@Deprecated
class Person extends A implements IA, IB {
//属性
public String name;
protected int age;
String job;
private double sal;
//方法
public void m1() {
}
protected void m2() {
}
void m3() {
}
private void m4() {
}
public Person() {
}
public Person(String name, int age, String job, double sal) {
this.name = name;
this.age = age;
this.job = job;
this.sal = sal;
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
private Person(String name) {
this.name = name;
}
}
1、2 第二组:java.lang.reflect.Field
1、getModifiers:以int形式返回修饰符
默认为-0 public-1 private-2 protect-4 static-8 final-16
public static = 1+8 = 9
2、getType:以Class形式返回
3、getName返回属性名字
//得到class对象
Class<?> personClass = Class.forName("com.demo.reflection.Person");
Field[] declaredFields = personClass.getDeclaredFields();
System.out.println("===========1==============");
//1、getModifiers:以int形式返回修饰符 默认为-0 public-1 private-2 protect-4 static-8 final-16
//public static = 1+8 = 9
Arrays.stream(declaredFields).forEach(declaredField -> {
System.out.println("属性名:"+declaredField.getName()+" 该属性的修饰符:"+declaredField.getModifiers()); //name age job sal
});
//属性名:name 该属性的修饰符:1
//属性名:age 该属性的修饰符:4
//属性名:job 该属性的修饰符:0
//属性名:sal 该属性的修饰符:2
//2、getType:以Class形式返回
System.out.println("===========2============");
Arrays.stream(declaredFields).forEach(declaredField -> {
System.out.println("属性名:"+declaredField.getName()+" 该属性的类型:"+declaredField.getType()); //name age job sal
});
//属性名:name 该属性的类型:class java.lang.String
//属性名:age 该属性的类型:int
//属性名:job 该属性的类型:class java.lang.String
//属性名:sal 该属性的类型:double
//3、getName返回属性名字
1、3 第三组:java.lang.reflect.Mehtod
1、getModifiers:以int形式返回修饰符
默认为-0 public-1 private-2 protect-4 static-8 final-16
public static = 1+8 = 9
2、getReturnType:以Class形式返回
3、getName返回属性名字
4、getParameterTypes: 以Class[] 返回参数类型数组
1、4 第四组:java.lang.reflect.Constructor
1、getModifiers 以int的形式返回修饰符
2、getName:返回构造器名
3、getParameterTypes: 以Class[] 返回参数类型数组
2、反射暴破
2、1 反射暴破创建对象
通过反射创建创建对象
public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {
//1、 先获取到User类的class对象
Class<?> userClass = Class.forName("com.demo.reflection.User");
//2、 通过public的无参构造器创建实例
Object o = userClass.newInstance();
System.out.println(o);//User{age=10, name='初始名字'}
//3、 通过public的有参构造器创建实例
Constructor<?> constructor = userClass.getConstructor(String.class);/**
/*
* constructor就是我们的构造器:public User(String name) {
*/
Object hahaha = constructor.newInstance("hahaha");
System.out.println(hahaha);//User{age=10, name='hahaha'}
//4、 通过非public的有参构造器创建实例
Constructor<?> declaredConstructor = userClass.getDeclaredConstructor(int.class, String.class);
declaredConstructor.setAccessible(true);//暴破【暴力破解】,使用反射可以访问private构造器
Object heiheie = declaredConstructor.newInstance(2, "heiheie");
System.out.println(heiheie);//User{age=2, name='heiheie'}
}
类
class User {
private int age = 10;
private String name = "初始名字";
public User() {
}
public User(String name) {
this.name = name;
}
private User(int age, String name) {
this.age = age;
this.name = name;
}
@Override
public String toString() {
return "User{" +
"age=" + age +
", name='" + name + '\'' +
'}';
}
}
问:我们对一个私有的属性,构造器或者是方法 我们能不能访问?
能。可以用反射,在反射面前一切都是纸老虎,破坏了封装性。
2、2 通过反射访问类中的成员
访问属性
class Student{
public int age;
private static String name;
public Student(){
}
@Override
public String toString() {
return "Student{" +
"age=" + age +
"name="+name+
'}';
}
}
public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchFieldException {
//1. 得到student类对应的Class对象
Class<?> studentClass = Class.forName("com.demo.reflection.Student");
//2. 创建对象
Object o = studentClass.newInstance();//o的运行类型就是student
System.out.println(o.getClass());//查看运行类型---class com.demo.reflection.Student
//3. 使用反射得到age 属性对象
Field age = studentClass.getField("age");
age.set(o,88);//通过反射来操作属性
System.out.println(o);//Student{age=88 name=null}
System.out.println(age.get(o));//直接返回属性的值---88
//4. 使用反射操作name 属性 (私有的 静态的)
Field name = studentClass.getDeclaredField("name");
//对name进行暴破
name.setAccessible(true);
name.set(o,"das");
//name.set(null,"das"); //name是static属性,因此o 也可以写成null
System.out.println(o);//Student{age=88name=das}
System.out.println(name.get(o));//获取属性值
System.out.println(name.get(null));//获取属性值(name为静态的)
}
访问方法
class Boss {
public int age;
private static String name;
public Boss() {
}
private static String say(int n, String s, char c) {
return n + " " + s + " " + c;
}
public void hi(String s){
System.out.println("hi: "+s);
}
}
public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {
//1、得到Boss类 对应的Class对象
Class<?> bossClass = Class.forName("com.demo.reflection.Boss");
//2、创建对象
Object o = bossClass.newInstance();
//3、调用public的hi方法
//Method hi = bossClass.getMethod("hi",String.class);//获取公有的方法 这个和下面的额方法都可以
//3.1得到hi方法对象
Method hi1 = bossClass.getDeclaredMethod("hi",String.class);//获取所有的方法
//3.2 调用
Object o1 = hi1.invoke(o, "111");//hi: 111
Method say = bossClass.getDeclaredMethod("say", int.class, String.class, char.class);
say.setAccessible(true);
Object invoke = say.invoke(o, 100, "张三", '男');
System.out.println(invoke);//100 张三 男
}