JAVA反射
反射 (框架)
一个类或者对象通过反射可以获得自身的对象,该对象是一个java.lang.Class 的对象。
一个对象或者类获得自身的Class对象的过程称为反射。
有两种方法可以获得自身的Class对象引用(对每一个被装载的类型(类或接口),
虚拟机都会为它创建一个java.lang.Class的实例):
1) Class c = Class.forName(“PackageName.ClassName”);//虚拟机中没有该类的Class的实例对象
2) Class c = t.getClass();//虚拟机已经存在Class的实例对象
Class c = this.getClass();//虚拟机已经存在Class的实例对象
注意:类和它所创建的所有对象通过反射获得的Class对象都是同一个
反射可以让我们利用这个Class对象来获取和修改私有的变量和方法,不通过公有的(public)方法来设置和获取私有的变量,可以破坏数据的封装性。
常用到反射方式:
1) 创建对象
2) 访问对象中的属性
3) 访问对象中的方法
4) 访问对象中的构造器
通过反射机制可以写出通用性很好的程序,对系统编程来说特别有用,但它并不适合于应用编程。而且,反射是脆弱的——编译不能帮助你发现编译错误,任何错误在运行时被发现并且都会导致异常。
*创建反射的步骤:
1) Class c=Class.forName("package.name");创建Class对象
2) Constructor cons = c.getConstructor(int.class,String.class);//获取有参构造器(无参去掉参数即可)
3) Object o=cons.newInstance(1,"String");//创建对象的实例(无参去掉参数即可)
4) Method method =c.getMethod("name");//获取指定方法(getDeclaredMethod()获取指定私有方法)
5) method.invoke(o);//调用相应对象的方法
--------------------------------------------------------------------------------------------------
例子:
package t;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
public class reflect {
int a;
private String b;
public reflect(){}
private void name(){
System.out.println("name私有方法 "+a+" | "+b);
}
public reflect(int a,String b){
this.a=a;
this.b=b;
}
public static void main(String[] args) throws Exception {
Class c=Class.forName("t.reflect");//获取类的Class对象
//Constructor cons = c.getDeclaredConstructor();//获取私有无参构造器
Constructor cons = c.getConstructor(int.class,String.class);//获取有参构造器
Object o=cons.newInstance(1,"testB");//创建对象
((reflect) o).name();//类型转换后可执行
Method method =c.getDeclaredMethod("name");//获取指定私有方法
method.invoke(o);//执行相应对象的方法
System.out.println();
Field[] f = c.getDeclaredFields();//获取所有属性(公有和私有)
System.out.println(f.length);//属性个数
for(Field ff : f){
ff.setAccessible(true);//true时可以访问private属性,在本例中由于是同一个类,所以不加也行
System.out.print(ff+" | ");//属性类型
System.out.print(ff.getName()+" | ");//属性名
System.out.println(ff.getModifiers());//属性值
}
}
}
控制台输出:
name私有方法 1 | testB
name私有方法 1 | testB
2
int t.reflect.a | a | 0
private java.lang.String t.reflect.b | b | 2
--------------------------------------------------------------------------------------------------
一个类或者对象通过反射可以获得自身的对象,该对象是一个java.lang.Class 的对象。
一个对象或者类获得自身的Class对象的过程称为反射。
有两种方法可以获得自身的Class对象引用(对每一个被装载的类型(类或接口),
虚拟机都会为它创建一个java.lang.Class的实例):
1) Class c = Class.forName(“PackageName.ClassName”);//虚拟机中没有该类的Class的实例对象
2) Class c = t.getClass();//虚拟机已经存在Class的实例对象
Class c = this.getClass();//虚拟机已经存在Class的实例对象
注意:类和它所创建的所有对象通过反射获得的Class对象都是同一个
反射可以让我们利用这个Class对象来获取和修改私有的变量和方法,不通过公有的(public)方法来设置和获取私有的变量,可以破坏数据的封装性。
常用到反射方式:
1) 创建对象
2) 访问对象中的属性
3) 访问对象中的方法
4) 访问对象中的构造器
通过反射机制可以写出通用性很好的程序,对系统编程来说特别有用,但它并不适合于应用编程。而且,反射是脆弱的——编译不能帮助你发现编译错误,任何错误在运行时被发现并且都会导致异常。
*创建反射的步骤:
1) Class c=Class.forName("package.name");创建Class对象
2) Constructor cons = c.getConstructor(int.class,String.class);//获取有参构造器(无参去掉参数即可)
3) Object o=cons.newInstance(1,"String");//创建对象的实例(无参去掉参数即可)
4) Method method =c.getMethod("name");//获取指定方法(getDeclaredMethod()获取指定私有方法)
5) method.invoke(o);//调用相应对象的方法
--------------------------------------------------------------------------------------------------
例子:
package t;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
public class reflect {
int a;
private String b;
public reflect(){}
private void name(){
System.out.println("name私有方法 "+a+" | "+b);
}
public reflect(int a,String b){
this.a=a;
this.b=b;
}
public static void main(String[] args) throws Exception {
Class c=Class.forName("t.reflect");//获取类的Class对象
//Constructor cons = c.getDeclaredConstructor();//获取私有无参构造器
Constructor cons = c.getConstructor(int.class,String.class);//获取有参构造器
Object o=cons.newInstance(1,"testB");//创建对象
((reflect) o).name();//类型转换后可执行
Method method =c.getDeclaredMethod("name");//获取指定私有方法
method.invoke(o);//执行相应对象的方法
System.out.println();
Field[] f = c.getDeclaredFields();//获取所有属性(公有和私有)
System.out.println(f.length);//属性个数
for(Field ff : f){
ff.setAccessible(true);//true时可以访问private属性,在本例中由于是同一个类,所以不加也行
System.out.print(ff+" | ");//属性类型
System.out.print(ff.getName()+" | ");//属性名
System.out.println(ff.getModifiers());//属性值
}
}
}
控制台输出:
name私有方法 1 | testB
name私有方法 1 | testB
2
int t.reflect.a | a | 0
private java.lang.String t.reflect.b | b | 2
--------------------------------------------------------------------------------------------------