天天看點

反射詳解

反射

1.反射java語言中的一種機制,通過這種機制可以動态的執行個體化對象、讀寫屬性、調用方。

2.一切反射相關的代碼都從獲得類對象開始

三種擷取的方法

(1) Class.forName(完整類名)

(2) 類名.class

(3) 對象.getClass()

注:1.ClassNotFoundException(類名錯|少jar包)。

2.統一類的類對象隻會建立一個。

3.首先為反射的操作創一個實體類

public class Student {
	private String sid;

	private String sname;
    String md;
	public Integer age;
	protected String sex;

	public String getSex() {
		return sex;
	}

	public void setSex(String sex) {
		this.sex = sex;
	}

	public Student() {
		super();
		System.out.println("調用無參構造方法建立了一個學生對象");
	}

	public Student(String sid) {
		super();
		this.sid = sid;
		System.out.println("調用帶一個參數的構造方法建立了一個學生對象");
	}

	public Student(String sid, String sname) {
		super();
		this.sid = sid;
		this.sname = sname;
		System.out.println("調用帶二個參數的構造方法建立了一個學生對象");
	}

	@SuppressWarnings("unused")
	private Student(Integer age) {
		System.out.println("調用Student類私有的構造方法建立一個學生對象");
		this.age = age;
	}

	public String getSid() {
		return sid;
	}

	public void setSid(String sid) {
		this.sid = sid;
	}

	public String getSname() {
		return sname;
	}

	public void setSname(String sname) {
		this.sname = sname;
	}

	public void hello() {
		System.out.println("你好!我是" + this.sname);
	}

	public void hello(String name) {
		System.out.println(name + "你好!我是" + this.sname);
	}

	@SuppressWarnings("unused")
	private Integer add(Integer a, Integer b) {
		return new Integer(a.intValue() + b.intValue());
	}
}

           

4.通過反射擷取構造方法。

下面main2、main3都隻是取的一個名字,目的是阻止其幹擾main運作,讓main運作

public class Demo {
	//私有構造方法
	public static void main(String[] args) throws Exception{
	 //擷取其全限定名com.demo.Student
		Class class1 = Class.forName("com.demo.Student");
		//擷取私有的需要在Constaructor前面加Declared。
		//Integer.class用其構造方法的屬性點class,有幾個屬性就寫幾個。
		Constructor con=class1.getDeclaredConstructor(Integer.class);
		//需要擷取權限
		con.setAccessible(true);
		con.newInstance(1);
		
	}
	//二參構造方法
	public static void main3(String[] args) throws Exception {
		Class class1 = Class.forName("com.demo.Student");
		Constructor con=class1.getConstructor(String.class,String.class);
		con.newInstance("S001","zs");
	}
	
	//一參構造方法
	public static void main2(String[] args) throws Exception {
		Class class1 = Class.forName("com.demo.Student");
		Constructor con=class1.getConstructor(String.class);
		con.newInstance("S001");
	}
	
    //無參構造方法
	public static void main1(String[] args) throws Exception {
		Class class1 = Class.forName("com.demo.Student");
		Constructor con=class1.getConstructor();
		con.newInstance();
	}
	
}
           

5.用反射擷取方法

public class Demo1 {

	//私有方法
	public static void main(String[] args) throws Exception{
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
		//Method擷取對象方法一個方法,擷取私有的在前面加Declared
		//"add",Integer.class,Integer.class,先寫你要擷取的方法的名字,然後用其中的屬性去點class。
		Method m=class1.getDeclaredMethod("add",Integer.class,Integer.class);
		m.setAccessible(true);
		//m.invoke(obj,1,2)指派
		System.out.println(m.invoke(obj,1,2));
	}
	
	//有參方法
	public static void main2(String[] args)throws Exception {
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
		Method m=class1.getMethod("hello",String.class);
		m.invoke(obj, "zs");
		
	}
	
	//無參方法
	public static void main1(String[] args)throws Exception {
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
		Method m=class1.getMethod("hello");
		m.invoke(obj);
	}
	
}
           

6.用反射擷取屬性。

public class Demo2 {
	//保護的sex
	public static void main(String[] args) throws Exception{
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
		//擷取屬性的方法Field(要擷取的屬性);
	    Field field =class1.getDeclaredField("sex");
        field.setAccessible(true);
        field.set(obj, "男");//指派
        //field.get();擷取值
        System.out.println(field.get(obj));
		
	}
	
	//sname
	public static void main3(String[] args) throws Exception{
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
	    Field field =class1.getDeclaredField("sname");
		field.setAccessible(true);
		field.set(obj, "zs");
		System.out.println(field.get(obj));
		
	}
	

	//sid
	public static void main2(String[] args) throws Exception{
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
	    Field field =class1.getDeclaredField("sid");
	    field.setAccessible(true);
	    field.set(obj, "S001");
	    System.out.println(field.get(obj));
		
		
	}
	
	//公開的年齡
	public static void main1(String[] args) throws Exception{
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
	    Field field = class1.getField("age");
	    field.set(obj,12);
	   System.out.println( field.get(obj));
	}
}

           

7.用反射來擷取修飾符

擷取的修飾符會以數字的形式顯示。

private String sname;

String md;

public Integer age;

protected String sex;

//md 預設的修飾符
			public static void main(String[] args) throws Exception{
				Class class1 = Class.forName("com.demo.Student");
				Object obj = class1.newInstance();
			    Field field =class1.getDeclaredField("md");
			    //擷取修飾符的方法:field.getModifiers();
		        int i = field.getModifiers();
		        System.out.println(i);
			}
	//sex 保護的修飾符
		public static void main3(String[] args) throws Exception{
			Class class1 = Class.forName("com.demo.Student");
			Object obj = class1.newInstance();
		    Field field =class1.getDeclaredField("sex");
	        int i = field.getModifiers();
	        System.out.println(i);
		}

	//age公共的修飾符
	public static void main2(String[] args) throws Exception{
		Class class1 = Class.forName("com.demo.Student");
		Object obj = class1.newInstance();
	    Field field =class1.getDeclaredField("age");
        int i = field.getModifiers();
        System.out.println(i);
	}
	//sname私有的修飾符
		public static void main1(String[] args) throws Exception{
			Class class1 = Class.forName("com.demo.Student");
			Object obj = class1.newInstance();
		    Field field =class1.getDeclaredField("sname");
	        int i = field.getModifiers();
	        System.out.println(i);
		}

}