1,创建Person类
package reflect;
import java.io.InputStream;
import java.util.List;
public class Person {
public String name="aaaaa";
private int password;
private static int age;
public Person() {
System.out.println("person");
}
public Person(String name){
System.out.println("person "+name);
}
public Person(String name,int password){
System.out.println("person "+name+":"+password);
}
private Person(List<?> list){
for(int i=0;i<list.size();i++){
System.out.println("person "+list.get(i));
}
}
public void aa1(){
System.out.println("aa1");
}
public void aa1(String name,int password){
System.out.println("aa1 "+name+":"+password);
}
public Class[] aa1(String name,int[] password){
return new Class[]{String.class};
}
private void aa1(InputStream in){
System.out.println(in);
}
public static void aa1(int num){
System.out.println(num);
}
public static void main(String[] args){
System.out.println("main");
for(int i=0;i<args.length;i++){
System.out.println(args[i]);
}
}
}
2,反射测试类
package reflect;
import java.io.FileInputStream;
import java.io.InputStream;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.List;
import org.junit.Test;
/**
* java反射
* 加载类三种方式:
* 1、Class c=Class.forName("reflect.Person");
* 2、Class c=new Person().getClass();
* 3、Class c=Person.class;
*
*/
public class DemoTest {
/**
* 调无参构造
*/
@Test
public void constructor1() throws Exception{
Class c=Class.forName("reflect.Person");
Constructor cs=c.getConstructor(null);//null表示无参构造,null也可以不写
Person p=(Person) cs.newInstance(null);//调用无参构造函数创建实例,null可以不写
System.out.println(p.name);
}
/**
* 调有参构造Person(String name)
*/
@Test
public void constructor2() throws Exception{
Class c=Class.forName("reflect.Person");
Constructor cs=c.getConstructor(String.class);//创建有参构造,参数类型为String
Person p=(Person) cs.newInstance("xxxx");//调用Person(String name)构造创建实例,xxxx可为任意字符串
System.out.println(p.name);
}
/**
* 调有参构造Person(String name,int password)
*/
@Test
public void constructor3() throws Exception{
Class c=Class.forName("reflect.Person");
Constructor cs=c.getConstructor(String.class,int.class);//创建有参构造,参数类型为String,int
Person p=(Person) cs.newInstance("xxxx",11);//调用Person(String name,int password)构造创建实例,xxxx可为任意字符串,11可为任意数字
System.out.println(p.name);
}
/**
* 调私有构造private Person(List list)
* 理论上私有方法外部类不可以访问,但是反射可以做到
*/
@Test
public void constructor4() throws Exception{
List<String> list=new ArrayList<String>();
list.add("aaa");
list.add("bbb");
list.add("ccc");
Class c=Class.forName("reflect.Person");
Constructor cs=c.getDeclaredConstructor(List.class);//私有构造用getDeclaredConstructor获取
cs.setAccessible(true);//爆力反射,可以访问私有方法
Person p=(Person) cs.newInstance(list);
System.out.println(p.name);
}
/**
* 无参构造第二种调用方式
*/
@Test
public void constructor5() throws Exception{
Class c=Class.forName("reflect.Person");
Person p=(Person) c.newInstance();
System.out.println(p.name);
}
/**
* 调public void aa1()方法
*/
@Test
public void method1() throws Exception{
Person person=new Person();
Class c=Class.forName("reflect.Person");
Method method=c.getMethod("aa1", null);//访问aa1方法,参数为null
method.invoke(person, null);//指定调哪个对象的方法,参数为null
}
/**
* 调public void aa1(String name,int password)方法
*/
@Test
public void method2() throws Exception{
Person person=new Person();
Class c=Class.forName("reflect.Person");
Method method=c.getMethod("aa1", String.class,int.class);
method.invoke(person, "TOM",32);
}
/**
* 调public Class[] aa1(String name,int[] password)方法
*/
@Test
public void method3() throws Exception{
Person person=new Person();
Class c=Class.forName("reflect.Person");
Method method=c.getMethod("aa1", String.class,int[].class);
Class[] cs=(Class[]) method.invoke(person,"Jack", new int[]{1,23});
System.out.println(cs[0]);
}
/**
* 调private void aa1(InputStream in)方法
*/
@Test
public void method4() throws Exception{
Person person=new Person();
InputStream is=new FileInputStream("D:\\work\\struts2\\src\\struts.xml");
Class c=Class.forName("reflect.Person");
Method method=c.getDeclaredMethod("aa1", InputStream.class);//访问私有方法用getDeclaredMethod
method.setAccessible(true);
method.invoke(person, is);
}
/**
* 调public static void aa1(int num)
*/
@Test
public void method5() throws Exception{
Class c=Class.forName("reflect.Person");
Method method=c.getMethod("aa1", int.class);//访问私有方法用getDeclaredMethod
method.invoke(null, 23);//静态方法调用不需要传对象
}
/**
* 反射创建实例并调用方法
*/
@Test
public void method6() throws Exception{
Class c=Class.forName("reflect.Person");
Constructor cs=c.getConstructor(null);
Person p=(Person) cs.newInstance(null);
Method m=c.getMethod("aa1", String.class,int.class);
m.invoke(p, "Lucy",45);
}
/**
* 反射调main方法
*/
@Test
public void method7() throws Exception{
Class c=Class.forName("reflect.Person");
Method method=c.getMethod("main", String[].class);
//method.invoke(null, new Object[]{new String[]{"aaa","bbb"}});//这里和其他方法不同,比较奇葩,两种调用方式
method.invoke(null, (Object)new String[]{"aaa","bbb"});
}
/**
* 反射字段属性 public String name="aaaaa";
*/
@Test
public void property1() throws Exception{
Person person=new Person();
Class c=Class.forName("reflect.Person");
Field field = c.getField("name");//获取名为"name"的字段
Class<?> type = field.getType();
System.out.println(type);//得到字段类型
String name=(String) field.get(person);
System.out.println(name);//得到字段值
//Object value=field.get(person);
//Class<?> type2 = field.getType();
//if(String.class.equals(type2)){
// String sValue=(String)value;
// System.out.println(sValue);
//}
field.set(person, "bbbb");//给该字段赋值为bbbb
System.out.println(person.name);
}
/**
* 反射私有属性private int password;
*/
@Test
public void property2() throws Exception{
Person person=new Person();
Class c=Class.forName("reflect.Person");
Field field = c.getDeclaredField("password");
field.setAccessible(true);
field.set(person, 123456);
int password = (Integer) field.get(person);
System.out.println(password);
}
/**
* 反射私有静态属性private static int age;
*/
@Test
public void property3() throws Exception{
Class c=Class.forName("reflect.Person");
Field field = c.getDeclaredField("age");
field.setAccessible(true);
field.set(null, 87);
int age = (Integer) field.get(null);
System.out.println(age);
}
}