您的位置:首页 > 职场人生

黑马程序员——09 高新技术(二)一个例子学会使用反射机制

2014-06-27 15:30 465 查看
  ------- android培训java培训、期待与您交流! ----------

当我们写好一个程序时,Java 语言把每个单独的类 Class 和接口 Implements 编译成单独的一个 . class 文件,这些文件对于 Java 运行环境来说就是一个个可以动态加载的单元。此外这些class文件就是这些类或接口的字节码文件,为了操作这些字节码文件,java把这些字节码文件归为Class类。

那么怎样来理解Class类呢?

类就是一些具有相同特性的对象的抽象形式,比如Person类,就把人的姓名,年龄,身高等共有的数据给抽象出来。

而Class类就是所有类字节码文件对象的抽象形式,所有的类都是具有字段,构造方法,成员方法这些相同的元素,

Class类就把这些类共有的特性分为了Field,Constructor,Method类。

而反射就是建立在Class类的基础上来动态的获取类中的信息,调用这些类的方法和属性,要想操作这些类必须先获得这些类的字节码文件对象。比如Person类就具有自己特有的字节码文件,他的对象P1和P2所对应的类的字节码文件都是一样的。

下面通过一个例子就把关于反射的大部分操作方法给展现出来。

[java] view
plaincopy

//定义一个Person类,分别有公有和私有的构造方法、字段和方法,然后用反射来操作这个类  

public class Person {  

    private String namePrivate;  

    public static int ageStatic;  

    public String namePublic;  

    public int agePublic;  

      

      

     Person() {  

          

    }  

      

    public Person(String namePublic,int agePublic)  

    {  

        this.namePublic = namePublic;  

        this.agePublic = agePublic;  

        System.out.println("我是公有构造方法"+"公有字段"+namePublic+agePublic);  

    }  

      

    public Person(int agePublic)  

    {  

        this.agePublic = agePublic;  

    }  

      

    private Person(String namePrivate)  

    {  

        this.namePrivate = namePrivate;  

        System.out.println("我是私有有构造方法"+"私有字段"+namePrivate);  

    }  

  

    public Person getPersonPublic(String namePublic ,int agePublic )  

    {  

        this.agePublic = agePublic;  

        this.namePublic = namePublic;  

        Person p = new Person();  

        return p;  

    }  

      

    public int  getAgePublic()//空参数的构造方法  

    {  

        return agePublic;  

    }  

      

    private String getNamePrivate(String name)  

    {  

        return namePrivate;  

    }  

      

    public static int getAgeStatic(int age)  

    {  

        Person.ageStatic = age;  

        return ageStatic;  

    }  

}  

 

[java] view
plaincopy





import java.lang.reflect.Constructor;  

  

  

import java.lang.reflect.Field;  

import java.lang.reflect.Method;  

  

import javax.activation.FileDataSource;  

  

import cn.cn.cn.Student;  

  

public class ClassDemo {  

  

    public static void main(String[] args) throws Exception  

    {  

        new Student();  

        /* 

         * 有三种方式可以得到Person类的Class 

         * 方式一:知道Person的一个对象p 

         *        Class c1 = p.getClass(); 

         * 方式二:知道有个类叫Person   

         *        Class c2 = Person.class; 

         * 方式三:知道有个类叫Person  此种方式的字符串参数要包括包名,一般是通过配置文件获得的 

         *        Class c3 = Class.forName("Person"); 

         */  

          

         //方式一:必须要先有个对象  

         Person p = new Person();  

         Class c1 = p.getClass();  

           

         //方式二  

         Class c2 = Person.class;  

           

//       方式三  

         Class c3 = Class.forName("Person");//Person保存在默认包中  

         //如果我们定义一个Student类他的包名为 cn.cn.cn,用之前先导入包,最上面:import cn.cn.cn.Student;  

         Class c4 = Class.forName("cn.cn.cn.Student");  

         System.out.println(c4);  

         /* 

1         * 构造方法的获得方式 

          *  

          * 1.获得公有的构造方法 

          *  1.1获得所有的公有方法 

          *  1.2获得指定的公有方法 

          * 2.获得所有的构造方法 

          *  2.1获得所有的方法 

          *  2.2获得指定的私有方法 

          */  

           

         //1.1获得所有公有的构造方法,调用Class对象的getConstructors方法,他会返回返回一个包含某些 Constructor 对象的数组  

             Constructor[] cons = c1.getConstructors();  

             for(Constructor s : cons)  

             {  

                 System.out.println(s); //打印结果public Person(int)  public Person(java.lang.String,int)  

               

             }  

           // 1.2 获得指定的公有方法,调用Class方法的getConstructor方法,返回一个 Constructor 对象,它反映此 Class 对象所表示的类的指定公共构造方法。  

                 //指定的方法就是将构造方法的参数值传入  

             Constructor con = c1.getConstructor(String.class,int.class);  

             System.out.println(con);  //  public Person(java.lang.String,int)  

              

           // 2.获得所有的私有方法以及指定的私有方法,与上面的方法类似,就多了个Declared关键字  

             Constructor[] conprs = c1.getDeclaredConstructors();  

             Constructor conpr = c1.getDeclaredConstructor(String.class);  

             

    /***************************************************************************************/  

     /* 

2      * 获得字段的方法 

        2.1获得所有的公有字段 

        2.2获得所有的字段 

        2.3获得指定的私有字段 

         

      */       

               

        //获得所有的公有字段  

             Field[] filed = c1.getFields();   

        //获得所有的 私有有字段       

             Field[] fieldpr = c1.getDeclaredFields();  

        //获得指定的私有字段namePrivate  

             Field f = c1.getDeclaredField("namePrivate");  

             System.out.println(f);  

   /***************************************************************************************/       

 /* 

3     * 获得字段的方法 

         3.1获得所有的公有方法 

         3.2获得所有的方法 

         3.3获得指定的公有方法 

         3.4获得静态方法 

*/            

    //3.1获得所有的公有方法  

          Method []  ms = c1.getMethods();  

    //3.1获得所有的方法       

          Method []  mps = c1.getDeclaredMethods();  

    //3.3获得指定的公有方法,调用getDeclaredMethod(String name ,Class<?>... parameterTypes)  

    //  他又两个参数,name 参数是一个 String,它指定所需方法的简称,parameterTypes 参数是 Class 对象的一个数组,  

    //它按声明顺序标识该方法的形参类型。    

          Method m = c1.getDeclaredMethod("getNamePrivate", String.class);  

          //如果想获取空参数的构造方法,将参数表写为null就行了  

           Method mnull = c1.getMethod("getAgePublic", null);  

    //3.4获得静态方法,和普通的获得方法没什么不同  

          Method mm = c1.getMethod("getAgeStatic", int.class);  

          /***************************************************************************************/  

    /* 

4       如何利用反射实例化一个对象,并使用它的方法 

        4.1利用方式实例化一个对象 

           4.1.1利用默认的无参构造函数实例化一个对象 

           4.1.2利用指定的公共的构造函数实例化一个对象 

           4.1.3利用指定的私有的构造函数实例化一个对象 

            

                  

        4.2利用反射使用方法 

           4.2.1使用公共的方法 

           4.2.2使用私有的方法 

           4.2.3使用静态方法 

 *  */        

            

          // 4.1.1利用默认的无参构造函数实例化一个对象  

          Person p1 = (Person)c1.newInstance();  

          // 4.1.2利用指定的公共的构造函数实例化一个对象  

          Constructor con1 = c1.getConstructor(String.class,int.class);  

          Person p2 =  (Person)con1.newInstance("liming",20);  

          System.out.println(p2.agePublic+p2.namePublic);  

          //利用指定的私有的构造函数实例化一个对象  

          Constructor con3 = c1.getDeclaredConstructor(String.class);  

          //私有的必需要设置访问权限,否则不能访问,对于字段和方法也是一样的  

           con3.setAccessible(true);  

           con3.newInstance("wang");  

            

             

           // 4.2.1使用公共的方法  

           Method m1 = c1.getMethod("getAgePublic", null);  

           Object obj = c1.newInstance();  

             

           int age = (Integer) m1.invoke(obj, null);  

           //4.2.2使用私有的方法,与上面类似,只要设置权限就可以了  

           //4.2.3使用静态方法。和上面类似,只要invoke的第一个参数设为null  

           Method m2 = c1.getMethod("getAgeStatic", int.class);  

           int age1 = (Integer) m2.invoke(null, 24);  

           System.out.println(age1);  

             

             

    }  

}  

 

  ------- android培训java培训、期待与您交流! ----------
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
相关文章推荐