java反射机制

来源:互联网 发布:java中的接口是什么 编辑:程序博客网 时间:2024/06/10 16:49

1.Class类的使用
三种方法获得类类型Class c1 = myClass.class;Class c2 = myObject.getClass();Class c3 = Class.forName("com.myClass");任何类都是java.lang.class的实例通过类类型获得类对象myClass myObject =(myClass) c1.newInstance(); //需要有无参数的构造方法2.动态加载类new 创建对象是静态加载类,在编译时刻就需要加载所有的可能使用到的类缺点:100个类中有1个类发生错误,其他99个都不能使用使用动态加载类可以解决该问题//动态加载类,在运行时刻加载Class c=Class.forName(arg[0]);//通过类类型,创建该类对象OfficeAble oa=(OfficeAble)c.newInstance(); //这里有一个问题oa.start();Word w=(Word)c.newInstance();  如果c.newInstance()得到的是Excel类型怎么办?此时创建一个接口OfficeAble来约束规定它们,让它们都实现这个接口,无所谓是哪个类了/***对类类型的一些操作*///获取类的信息,首先获取类的类类型        Class c=obj.getClass();//传递的是哪个子类的对象,c就是该子类的类类型        System.out.println("类的名称是"+c.getName());        /*         * Method类,方法对象(万物皆对象)         * 一个成员方法就是一个Method对象         * getMethods()方法获取的是所有public的函数,包括父类继承而来的         * getDeclaredMethods()获取的是所有该类自己声明的方法,不问访问权限         */        Method[] ms=c.getMethods();// c.getDeclaredMethods()        for (int i = 0; i < ms.length; i++) {            //得到方法返回值类型的类类型            Class returnType=ms[i].getReturnType();            //得到方法名称            System.out.println(ms[i].getName());            //获取参数类型-->得到的是参数列表的类型的类类型            Class[] paramTypes=ms[i].getParameterTypes();            for (Class class1 : paramTypes) {                System.out.print(class1.getName()+",");            }                    }            }    /**     * 打印对象的构造函数的信息     * @param obj     */    public static void printConMessage(Object obj) {        Class c=obj.getClass();        /*         *构造函数也是对像         *java.lang.Constructor中封装了构造函数的信息         *getConstructor获取所有的public的构造函数         *getDeclaredConstructors()得到所有的构造函数         */        //Constructor[] cs=c.getConstructors();        Constructor[] cs=c.getDeclaredConstructors();        for (Constructor constructor : cs) {            System.out.print(constructor.getName()+"(");            //获取构造函数的参数列表-->得到的是参数列表的类类型            Class[] paramTypes=constructor.getParameterTypes();            for (Class class1 : paramTypes) {                System.out.print(class1.getName()+",");            }            System.out.println(")");        }    }
对方法类的一些操作

public class MethodDemo1 {

    public static void main(String[] args) {
        
        // 获取print(int ,int)方法   1.获取一个方法就是获取类信息,获取类的信息首先获取类类型
        A a1=new A();
        Class c=a1.getClass();
        /*
         * 2.获取方法 名称和参数列表来决定
         */
        try {
            //Method m=c.getMethod("print", new Class[]{int.class,int.class});
            Method m=c.getMethod("print", int.class,int.class);
            //方法的反射操作
            //a1.print(10, 20); 方法的反射操作是用m对象来进行方法的调用(两种调用效果完全相同)
            //方法没用返回值返回null,有返回值返回具体的返回值
            //Object object=m.invoke(a1, 10,20);
            //参数没有可不写
            Object object=m.invoke(a1, new Object[]{10,20});
            System.out.println("============================");
            Method m1=c.getMethod("print",String.class,String.class);
            Object object2=m1.invoke(a1, "hello","WORLD");
        } catch (Exception e) {
            e.printStackTrace();
        }

    }
}
class A{
    public void    print(int a,int b) {
        System.out.println(a+b);
    }
    public void print(String a,String b) {
        System.out.println(a.toUpperCase()+","+b.toLowerCase());
        
    }
}

public static void main(String[] args) {
        ArrayList list=new ArrayList();
        ArrayList<String> list1=new ArrayList<String>();
        list1.add("hello");
        Class c1=list.getClass();
        Class c2=list.getClass();
        System.out.println(c1==c2);
        //反射的操作都是编译之后的操做
        
        /*
         *c1==c2结果返回true说明编译之后集合是去泛型化的
         *java中集合的泛型,是防止错误输入的,只在编译阶段有效
         *绕过编译就无效了
         *验证:我们可以通过方法的反射来操作,绕过编译
         */
        try {
            Method m=c2.getMethod("add",Object.class);
            m.invoke(list1, 20);//绕过了编译就1绕过了泛型
            System.out.println(list1.size());
            System.out.println(list1);
        } catch (Exception e) {
            // TODO: handle exception
        }
    }

}
原创粉丝点击