黑马程序员----高新技术----之java反射

---------------------- android培训 、 java培训 、 期待与您交流! ------------------

1、学习反射,首先要了解Class类

    java类用于描述一类事物的共性,该类事物有什么属性,没有什么属性。
    Class类描述的信息:类的名字,类的访问属性,类所属于的包名,字段名称的列表,实现的接口、方法名称的列表等等。
    得到字节码对应的实例对象(Class类型)的三种方法:
            1、类名.class 如:System.class;
            2、对象.getClass() 如:new Date().getClass();
            3、Class.forName("类名") 如:Class.forName("java.util.Date"); //做反射的时候一般用这种。

            

2、九个预定义的Class实例对象:

    八个基本类型,加上void。即:Boolean, Character,Byte,Short,Integer,Long,Float,Double,Void.
   int.class == Integer.TYPE。
   查看是不是数组类型的Class实例对象用的是:Class.isArray().
   总之,只要是在源程序中出现的类型,都有各自的Class实例对象。

    

3、反射的定义及其用法:

     反射就是把java类中的各种成分映射成相应的java类。
    

  • 构造方法的反射:Constructor类代表某个类中的一个构造方法:

        得到某个类所有的构造方法----如:

               Constructor [] constructor = Class.forName("java.lang.String").getConstructor();
        得到某一个构造方法----如:

               Constructor [] constructor = Class.forName("java.lang.String").getConstructor(StringBuffer.class);
        用反射实现 new String(new StringBuffer("abc"));
            如下: Constructor con = String.class.getConstructor(StringBuffer.class);    
                        String str = (String)constructor.newInstance(new StringBuffer("abc"));
                    调用newInstance时要用到跟getConstructor中相同类型的实例对象。

                     也就是说上边第一句用了StringBuffer,第二句也必须是StringBuffer。
        Class.newInstance()方法:
            该方法内部先得到默认的构造方法,然后用该构造方法创建实例对象。
            例子:String obj = (String)Class.forName("java.lang.String").newInstance();
        

  • 成员变量的反射:Field类代表某个类中的一个成员变量。

        public class ReflectPoint{
            private int x;
            public int y;
            
            public ReflectPoint(int x, int y){
                super();
                this.x = x;
                this.y = y;
            }
        }
        public class ReflectTest{
            public static void main(String[] args) throws Exception {
                ReflectPoint pt1 = new ReflectPoint(3,5);
                Field fieldY = pt1.getClass().getField("y");//fieldY不是对象身上的变量,而是类上的,

                          要用它去取某个对象上对应的值。
                System.out.Println(fieldY.get(pt1));  //fieldY.get(pt1)取出pt1对象上变量的值。
                
                fieldX.setAccessble(true);        //暴力反射,不管是不是私有的,都可以取到。
                Field fieldX = pt1.getClass().getDeclaredField("x");
                System.out.Println(fieldX.get(pt1));
        
            }
        }
        
        成员变量反射的综合案例:
        public class ReflectString{
            public String str1 = "ball";
            public String str2 = "bass";
            public String str3 = "this is a to babaa";
            
            @Override
            public String toString(){
                return str1 + "..." + str2 + ";;;" + str3;
            }
        }
        
        import java.lang.reflect.*;

        public class ReflectTest{
            public static void main(String[] args) throws Exception {
                ReflectString rs = new ReflectString();

                changeStringValue(rs);
                System.out.println(rs);
            }
            private static void changeStringValue(Object obj) throws Exception{
                Field[] fields = obj.getClass().getFields();
                for(Field field : fields){
                    if(field.getType() == String.class){ //反射中用==比equals要好,因为字节码只有一个。
                        String oldValue = (String)field.get(obj);
                        String newValue = oldValue.replace('b','a');
                        field.set(obj, newValue);
                    }
                }
            }
        }
        输出为:aall...aass;;;this is a to aaaaa
        
    

  • 成员方法的反射:Method类代表某个类中的一个成员方法。

        得到类中的某一个方法:
            例子:Method charAt = Class.forName("java.lang.String").getMethod("charAt", int.class);
        调用方法:
            通常方式:System.out.println(str.charAt(1));
            反射方式:System.out.println(charAt.invoke(str,1));
                如果传递给Method对象的invoke()方法的第一个参数为null,说明该Method对象对应的是一个静态方法!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值