JAVA反射创建类对象与例题

(一)

1.概念

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

Class类的构造方法是private,由JVM创建。

反射是java语言的一个特性,它允程序在运行时(注意不是编译的时候)来进行自我检查并且对内部的成员进行操作。例如它允许一个java的类获取他所有的成员变量和方法并且显示出来。Java 的这一能力在实际应用中也许用得不是很多,但是在其它的程序设计语言中根本就不存在这一特性。例如,Pascal、C 或者 C++ 中就没有办法在程序中获得函数定义相关的信息。 (来自Sun)

JavaBean 是 reflection 的实际应用之一,它能让一些工具可视化的操作软件组件。这些工具通过 reflection 动态的载入并取得 Java 组件(类) 的属性。

反射是从1.2就有的,后面的三大框架都会用到反射机制,涉及到类”Class”,无法直接new CLass(),其对象是内存里的一份字节码.

Class 类的实例表示正在运行的 Java 应用程序中的类和接口。枚举是一种类,注释是一种接口。每个数组属于被映射为 Class 对象的一个类,所有具有相同元素类型和维数的数组都共享该 Class 对象。基本的 Java类型(boolean、byte、char、short、int、long、float 和 double)和关键字 void 也表示为 Class 对象。Class 没有公共构造方法。Class 对象是在加载类时由 Java 虚拟机以及通过调用类加载器中的 defineClass 方法自动构造的。

2.三种获取Class的方法

package com.forName03;

public class Test01 {
    public static void main(String[] args) throws ClassNotFoundException {
        person p = new person();
         //1、通过对象调用 getClass() 方法来获取,通常应用在:比如你传过来一个 Object
         //  类型的对象,而我不知道你具体是什么类,用这种方法
        Class c1 = p.getClass();

         //2、直接通过 类名.class 的方式得到,该方法最为安全可靠,程序性能更高
         //  这说明任何一个类都有一个隐含的静态成员变量 class
        Class c2 = person.class;
        //3、通过 Class 对象的 forName() 静态方法来获取,用的最多,
         //   但可能抛出 ClassNotFoundException 异常
        Class c3 = Class.forName("com.forName03.person");


        System.out.println(c1);//class com.forName03.person
        System.out.println(c2);//class com.forName03.person
        System.out.println(c3);//class com.forName03.person
    }
}

3.reflection 工作示例

public static void main(String args[]) {
            try {
                Class c = Class.forName("java.util.Stack");
                Method m[] = c.getDeclaredMethods();
                for (int i = 0; i < m.length; i++)
                    System.out.println(m[i].toString());
            } catch (Throwable e){
                System.err.println(e);
            }
        }
}
/*
public synchronized java.lang.Object java.util.Stack.pop()
public java.lang.Object java.util.Stack.push(java.lang.Object)
public boolean java.util.Stack.empty()
public synchronized java.lang.Object java.util.Stack.peek()
public synchronized int java.util.Stack.search(java.lang.Object)*/

4.显示对象类名

package com.forName;

public class Test03 {
    //显示对象的类名
    public static void main(String[] args) {
        person p =new person();
        printClassName(p);
        System.out.println("The name of class person is: "+person.class.getName());

    }
    static void printClassName(Object obj) {
        System.out.println("The class of " + obj +  " is " + obj.getClass().getName());
    }
//The class of com.forName.person@1b6d3586 is com.forName.person
    //The name of class person is: com.forName.person

}

(二)例题

1.将所有String类型的成员变量里的b改成a

package com.forName.example;
import java.lang.reflect.Field;

public class theString {
    public static void main(String[] args) throws SecurityException, NoSuchMethodException, NoSuchFieldException, IllegalArgumentException, Exception {
        ReflectPointer rp1 = new ReflectPointer(3,4);
        changeBtoA(rp1);
        System.out.println(rp1);
    }

    private static void changeBtoA(Object obj) throws RuntimeException, Exception {
        Field[] fields = obj.getClass().getFields();
        for(Field field : fields) {
            //if(field.getType().equals(String.class))
            // 由于字节码只有一份,用equals语义不准确
            if(field.getType()==String.class) {
                String oldValue = (String)field.get(obj);
                String newValue = oldValue.replace('b', 'a');
                field.set(obj,newValue);//设新值
            }
        }
    }
}

class ReflectPointer {
    private int x = 0;
    public int y = 0;
    public String str1 = "ball";
    public String str2 = "basketball";
    public String str3 = "itcat";
    public ReflectPointer(int x,int y) {
        //alt + shift +s相当于右键source super();
        // TODO Auto-generated constructor stub
        this.x = x; this.y = y;
    }
    @Override public String toString() {
        return "ReflectPointer [str1=" + str1 + ", str2=" + str2 + ", str3=" + str3 + "]";
    }
}
/*输出结果
* test{a=1, b=3}
 * */

2.模拟 instanceof 操作符

package com.forName.example;

public class instanceofTest {
         public static void main(String args[]) {
             try {
                 Class cls = Class.forName("com.forName.example.S");
                 boolean b1 = cls.isInstance(new Integer(37));
                 System.out.println(b1);
                 boolean b2 = cls.isInstance(new S());
                 System.out.println(b2);
             } catch (Throwable e) {
                 System.err.println(e);
             }
         }
         //false
        //true
}
class S {
}

在这个例子中创建了一个S 类的 Class 对象,然后检查一些对象是否是S的实例。new Integer(37) 不是,但 new S()是。

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值