Java SE————反射機制

反射:

  一. 什麼是反射?

          可以在運行時候,動態的查看到類(已經裝載到JVM中的Java對象)的所有屬性和方法,同時可以訪問類的任意方法和屬性,這種  方式就稱爲反射。
  

先來一個person.class

package reflect;

public class Person {
    //類在計算機語言中 描述現實生活中事物的屬性特徵和行爲

    public String name;
    public String sex;
    private int age;

    //構造方法是爲了用來創建對象使用的。主要用於初始化。
    //構造方法是和類名相同,參數不同。
    public Person() {
    }
    private Person(String name, String sex, int age) {
        this.name = name;
        this.sex = sex;
        this.age = age;

    }

    private void study(){
        System.out.println("我是"+name+"在學習java");
    }

    private void sleep(){
        System.out.println("我是"+name+"我要睡覺了");
    }

    @Override
    public String toString() {
        return "reflect.Person{" +
                "name='" + name + '\'' +
                ", sex='" + sex + '\'' +
                ", age=" + age +
                '}';
    }

    public String getName() {
        return name;
    }

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

    public String getSex() {
        return sex;
    }

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

    public int getAge() {
        return age;
    }

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


}

二.怎麼獲取類的Class對象
  

三個方式:

import java.lang.reflect.InvocationTargetException;

public class CreateClassObject {
    public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException, NoSuchFieldException {
        //加載.class文件,生成Class對象,Class對象的獲取方式
       
        //獲取Person的Class對象方式一:
        Class clasz = Class.forName("reflect.Person");
        
        //獲取Person的Class對象方式二:
        Class clasz1 =Person.class;
        
        //獲取Person的Class對象方式三:
        Person person =new Person();
        Class clasz2 =person.getClass();
    }
}


   三.怎麼獲取類的構造方法


       1.clazz.getContructors()    獲取所有的公有構造方法

        Class clasz = Class.forName("reflect.Person");
         
        //獲取所有公有的構造方法
        
        //返回值類型是一個Constructor型數組
        Constructor[] constructors = clasz.getConstructors();
        for (Constructor cons : constructors) {
            
            //利用toString()打印結果
            System.out.println(cons.toString());
        }


       2.clazz.getContructor()    獲取單個公有構造方法

  //獲取單個公有的無參構造方法
        Constructor constructor = clasz.getConstructor();
        System.out.println(constructor);
        Person person2 = (Person) constructor.newInstance();//調用構造方法創建對象
        person2.setName("hh");
        person2.setSex("男");
        person2.setAge(30);
        person2.study();


       3.clazz.getDeclaredContructors()   獲取所有的構造方法(包括公有和私有構造方法)

  //獲取所有的公有和私有的構造方法
        Constructor[] consts = clasz.getDeclaredConstructors();
        for (Constructor con : consts) {
            System.out.println(con.toString());
        }


    4.  clazz.getDeclaredContructor()    獲取單個構造方法(包括公有和私有構造方法)

 //獲取私有的構造方法
        Constructor constructor1 = clasz.getDeclaredConstructor(String.class); //傳入參數
        System.out.println(constructor1);

        constructor1.setAccessible(true);
            //把私有構造方法設置爲可訪問的
       
        Person person3 = (Person) constructor1.newInstance("hhh");
        person3.study();

  • 調用私有方法時,使用 constructor1.setAccessible(true);可以忽略修飾符。


   四.怎麼調用構造方法創建對象
      

       contructor.newInstance();
       contructor.newInstance("參數");


   五.怎麼獲取成員變量
      

       clazz.getFields()                     //獲取所有公有屬性
       clazz.getField()                       //獲取單個公有屬性
       clazz.getDeclaredFields()      //獲取所有的屬性(包括公有和私有屬性)
       clazz.getDeclaredField()        //獲取單個屬性(包括公有和私有屬性)

package reflect;

import java.lang.reflect.Field;

public class CreateFields {
    public static void main(String[] args) throws ClassNotFoundException, NoSuchFieldException {
        Class clasz = Class.forName("reflect.Person");

        //一、獲取類的所有公有成員變量
        Field[] fields = clasz.getFields();
        for (Field field : fields) {
            System.out.println(field.toString());
        }

        /*運行結果:public java.lang.String reflect.Person.name
                   public java.lang.String reflect.Person.sex*/

        //二、獲取單個公有成員變量
        Field name = clasz.getField("name");
        Field sex = clasz.getField("sex");
        //Field age = clasz.getField("age"); //age爲私有變量,運行報錯
        System.out.println(name);
        System.out.println(sex);
        //System.out.println(age);

        /*運行結果:public java.lang.String reflect.Person.name
        public java.lang.String reflect.Person.sex*/

        //三、獲取所有的變量(包括公有和私有的)
        Field[] fieldsq1 = clasz.getDeclaredFields();
        for (Field field : fieldsq1) {
            System.out.println(field.toString());      //私有變量age也會打印
        }
            System.out.printf(fieldsq1[2].toString()); //只打印age變量

        //四、獲取單個公有成員變量
        Field name1 = clasz.getDeclaredField("name"); //出入參數指定某個變量
        Field sex1 = clasz.getDeclaredField("sex");
        Field age1 = clasz.getDeclaredField("age");
        System.out.println(name1);
        System.out.println(sex1);
        System.out.println(age1);
    }
}


 六.  怎麼獲取方法


       clazz.getMethods()                //獲取所有公有方法
       clazz.getMethod()                  //獲取單個公有方法
       clazz.getDeclaredMethods()  //獲取所有的方法(包括公有和私有方法)
       clazz.getDeclaredMethod()   //獲取單個方法(包括公有和私有方法)

package reflect;

import java.lang.reflect.Method;

public class CreateMethods {
    public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException {
        Class clasz = Class.forName("reflect.Person");

        //一、獲取所有的公有方法
        Method[] methods = clasz.getMethods();
        for (Method method : methods) {
            System.out.println(method);
        }
             /*運行結果:(perseon默認繼承Object類)
                        public java.lang.String reflect.Person.toString()
                        public java.lang.String reflect.Person.getName()
                        public void reflect.Person.setName(java.lang.String)
                        public void reflect.Person.setAge(int)
                        public void reflect.Person.study()
                        public void reflect.Person.setSex(java.lang.String)
                        public int reflect.Person.getAge()
                        public java.lang.String reflect.Person.getSex()
                        public final void java.lang.Object.wait() throws java.lang.InterruptedException
                        public final void java.lang.Object.wait(long,int) throws java.lang.InterruptedException
                        public final native void java.lang.Object.wait(long) throws java.lang.InterruptedException
                        public boolean java.lang.Object.equals(java.lang.Object)
                        public native int java.lang.Object.hashCode()
                        public final native java.lang.Class java.lang.Object.getClass()
                        public final native void java.lang.Object.notify()
                        public final native void java.lang.Object.notifyAll()*/

         //二、獲取單個公有方法
        Method method =clasz.getMethod("study");
        System.out.println(method);
            /*運行結果:public void reflect.Person.study()*/

        //三、獲取所有的公有和私有方法
        Method[] methods2 = clasz.getDeclaredMethods();
        for (Method met : methods2) {
            System.out.println(met);
        }
            /*運行結果:私有方法sleep也獲取到了,private void reflect.Person.sleep()*/

        //四、獲取單個的私有或者公有方法
        Method studyMethod =clasz.getDeclaredMethod("study");
        Method sleepMethod =clasz.getDeclaredMethod("sleep");
        Method getAgeMethod =clasz.getDeclaredMethod("getAge");
        System.out.println(studyMethod);
        System.out.println(sleepMethod);
        System.out.println(getAgeMethod);
       
        /*運行結果: public void reflect.Person.study()
                    private void reflect.Person.sleep()
                    public int reflect.Person.getAge()*/
    }
}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章