Java反射

1. 定义

JAVA反射(放射)机制:“程序运行时,允许改变程序结构或变量类型,这种语言称为动态语言”。从这个观点看,Perl,Python,Ruby是动态语言,C++,Java,C#不是动态

语言。但是JAVA有着一个非常突出的动态相关机制:Reflection,用在Java身上指的是我们可以于运行时加载、探知、使用编译期间完全未知的classes。换句话说,Java程序

可以加载一个运行时才得知名称的class,获悉其完整构造(但不包括methods定义),并生成其对象实体、或对其fields设值、或唤起其methods。其中,有一个Class类型,

它是实现反射的起源,针对任何您想探勘的类,唯有先为它产生一个Class 对象,接下来才能经由后者唤起为数十多个的Reflection APIs。而关于jvm如何加载类的过程,见文

2. 实例应用

案例接口
public interface China {

	public void sayHello(String name, Integer age);
}

案例类
public class Person implements China{

	private int age;
	
	private String name;

	public int getAge() {
		return age;
	}

	public final void setAge(Integer age) {
		this.age = age;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	@Override
	public String toString() {
		return "Person [age=" + age + ", name=" + name + "]";
	}

	public Person(int age, String name) {
		super();
		this.age = age;
		this.name = name;
	}
	
	public Person(int age){
		super();
		this.age = age;
	}
	
	public Person(String name){
		super();
		this.name = name;
	}

	public Person() {
		super();
	}

	@Override
	public void sayHello(String name, Integer age) {
		System.out.println("hello "+ name + " : " + age);
	}
}


测试类
public class ReflectTest {

	/**
	 * 通过Class.forName和ClassLoader来加载类
	 * @throws ClassNotFoundException
	 */
	@Test
	public void test1() throws ClassNotFoundException{
		Class<?> demo1 = null;
		Class<?> demo2 = null;
		Class<?> demo3 = null;
		Class<?> demo4 = null;
		demo1 = Class.forName("cn.test.reflect.Demo");
		demo2 = new Demo().getClass();
		demo3 = Demo.class;
		demo4 = Demo.class.getClassLoader().loadClass("cn.test.reflect.Demo");
		System.out.println(demo1.getName());
		System.out.println(demo2.getName());
		System.out.println(demo3.getName());
		System.out.println(demo4.getName());
	}
	
	/**
	 * 通过Class.forName("").newInstance()生成新对象,调用的是无参构造函数
	 * @throws ClassNotFoundException
	 * @throws InstantiationException
	 * @throws IllegalAccessException
	 */
	@Test
	public void test2() throws ClassNotFoundException, InstantiationException, IllegalAccessException{
		Class<?> demo = Class.forName("cn.test.reflect.Person");
		Person person = (Person) demo.newInstance();
		person.setAge(12);
		person.setName("张三");
		System.out.println(person);
	}

	/**
	 * 打印出该类所有的信息:属性,方法,构造函数
	 * @throws ClassNotFoundException
	 */
	@Test
	public void test3() throws ClassNotFoundException{
		Class<?> demo = Class.forName("cn.test.reflect.Person");
		System.out.println("类属性");
		Field[] fields = demo.getDeclaredFields();
		for(Field field : fields){
			int mo = field.getModifiers();
			System.out.print(Modifier.toString(mo)+" ");
			System.out.print(field.getType().getName()+" ");
			System.out.print(field.getName());
			System.out.println();
		}
		System.out.println("所有方法");
		Method[] methods = demo.getDeclaredMethods();
		for(Method method : methods){
			Class<?>[] parms = method.getParameterTypes();
			int mo = method.getModifiers();
			System.out.print(Modifier.toString(mo)+" ");
			System.out.print(method.getName()+"(");
			int i=1;
			for(Class<?> parm : parms){
				System.out.print(parm.getName() + " arg"+i++);
				if(i<=parms.length){
					System.out.print(",");
				}
			}
			System.out.print(")");
			System.out.println();
		}
		
		Constructor<?>[] constructors = demo.getConstructors();
		System.out.print("构造方法:");
		for(Constructor<?> constructor : constructors){
			System.out.println();
			Class<?>[] parms = constructor.getParameterTypes();
			int mo = constructor.getModifiers();
			System.out.print(Modifier.toString(mo)+" ");
			System.out.print(constructor.getName()+"(");
			int i=1;
			for(Class<?> parm : parms){
				System.out.print(parm.getName() + " arg"+i++);
				if(i<=parms.length){
					System.out.print(",");
				}
			}
			System.out.print("){}");
		}
	}
	
	/**
	 * 获取接口
	 * @throws ClassNotFoundException 
	 */
	@Test
	public void test4() throws ClassNotFoundException{
		Class<?> demo = Class.forName("cn.test.reflect.Person");
		Class<?>[] intes = demo.getInterfaces();
		for(Class<?> interf : intes){
			System.out.println(interf.getName());
		}
	}
	
	/**
	 * 获取父类
	 * @throws ClassNotFoundException
	 */
	@Test
	public void test5() throws ClassNotFoundException{
		Class<?> demo = Class.forName("cn.test.reflect.Person");
		Class<?> superClass = demo.getSuperclass();
		System.out.println(superClass.getName());
	}
	
	/**
	 * 反射调用类的中任意方法,需要知道方法名
	 * @throws ClassNotFoundException 
	 * @throws IllegalAccessException 
	 * @throws InstantiationException 
	 * @throws SecurityException 
	 * @throws NoSuchMethodException 
	 * @throws InvocationTargetException 
	 * @throws IllegalArgumentException 
	 */
	@Test
	public void test6() throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, SecurityException, IllegalArgumentException, InvocationTargetException{
		Class<?> demo = Class.forName("cn.test.reflect.Person");
		Person person = (Person) demo.newInstance();
		Method sayHelloMethod = demo.getMethod("sayHello", String.class, Integer.class);
		sayHelloMethod.invoke(person, "张三", 20);
		
		Method setAgeMethod = demo.getMethod("setAge", Integer.class);
		setAgeMethod.invoke(person, 2);
		
		Method getAgeMethod = demo.getMethod("getAge");
		System.out.println(getAgeMethod.invoke(person));
		
		Method setNameMethod = demo.getMethod("setName", String.class);
		setNameMethod.invoke(person, "李四");
		
		Method getNameMethod = demo.getMethod("getName");
		System.out.println(getNameMethod.invoke(person));
		
		Method toStringMethod = demo.getMethod("toString");
		System.out.println(toStringMethod.invoke(person));
	}

	/**
	 * 反射设置属性值
	 * @throws ClassNotFoundException
	 * @throws InstantiationException
	 * @throws IllegalAccessException
	 * @throws NoSuchMethodException
	 * @throws SecurityException
	 * @throws IllegalArgumentException
	 * @throws InvocationTargetException
	 * @throws NoSuchFieldException 
	 */
	@Test
	public void test7() throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, SecurityException, IllegalArgumentException, InvocationTargetException, NoSuchFieldException{
		Class<?> demo = Class.forName("cn.test.reflect.Person");
		Person person = (Person) demo.newInstance();
		
		Field ageField = demo.getDeclaredField("age");
		ageField.setAccessible(true);
		ageField.set(person, 10);
		
		Field nameField = demo.getDeclaredField("name");
		nameField.setAccessible(true);
		nameField.set(person, "王武");
		
		System.out.println(person);
	}
}


posted @ 2014-11-27 16:31  marco_tan  阅读(176)  评论(0编辑  收藏  举报