java类的反射

工作中日常总结、查看!!!

1.反射的前提必须有Class类,还有反射影响性能,日常运用不多,主要是在框架等中利用。

2.使用反射需要获取Class类,这个上篇文章中以做总结,可以查看上篇文章

3.反射是对运行的中类,进行刨析获取类中的方法,成员信息等

一、利用反射获取构造方法并创建对象

1.1获取构造方法的四种方法

1. Constructor getConstructor(Class... parameterTypes) 只能获得public修饰的构造方法
2. Constructor getDeclaredConstructor(Class... parameterTypes) 可以是public、protected、(默认)、private修饰符的构造方法。   
3. Constructor[] getConstructors() 只能获得public的
4. Constructor[] getDeclaredConstructors()可以是public、protected、package-private、private修饰符的构造方法。

测试类:

测试类以及结果:

2.1根据获取的构造方法获取对应的类

T newInstance(Object... initargs)根据指定的参数创建对象,传入的参数一定要和原来构造方法的参数类型,顺序,个数要一致
void setAccessible(boolean flag)设置"暴力反射"——是否取消权限检查,true取消权限检查,false表示不取消

注:如果是获取非public,需要设置setAccessible为true,进行暴力获取。

二、获取类中的成员方法

一次获取一个方法:

Method getMethod 根据方法名和参数类型获得对应的方法对象,只能获得public的 
Method getDeclaredMethod根据方法名和参数类型获得对应的方法对象,包括private的

一次获取多个方法:
Method[] getMethods()获得类中的所有成员方法对象,返回数组,只能获得public修饰的且包含父类的
Method[] getDeclaredMethods()获得类中的所有成员方法对象,返回数组,只获得本类的,包含private修饰的

测试类:

public class ActionMethodPojo {

    public void eat(){
        System.out.println("eat方法执行了..." );
    }

    public void eat(String food){

        System.out.println("eat方法执行了..."+food) ;
    }

    public static  void drink(String food){
        System.out.println("静态方法执行了...喝" + food);
    }

    private int work(int a,int b){
        System.out.println("非public方法执行了..." +(a+b));
        return a+b;
    }

测试方法类:
public class getGirlMethod {
    public static void main(String[] args) throws Exception {
        Class<?> mCls = Class.forName("com.bank.pojo.ActionMethodPojo");
        /**
         * getMethod 和getDeclaredMethod 两个方法都只能一次获取一个方法
         * getMethod 方法只能获取public类型的方法
         * getDeclaredMethod 方法可以获取 public protected 默认 private 以及静态方法
         */
        Method eat1 = mCls.getMethod("eat");
        Method eat2 = mCls.getMethod("eat",String.class);
        Method drink = mCls.getDeclaredMethod("drink", String.class);
        Method work = mCls.getDeclaredMethod("work", int.class, int.class);
        //执行方法前需要获取一个实体类对象
        ActionMethodPojo pojo = (ActionMethodPojo) mCls.getDeclaredConstructor().newInstance();
        eat1.invoke(pojo);
        eat2.invoke(pojo,"猪蹄");
        //这里静态方法可以不传对象
        drink.invoke(null,"咖啡");

        //非public方法执行需要暴力反射,才能正常执行,否则报错
        work.setAccessible(true);
        Object result = work.invoke(pojo, 1, 9);
        System.out.println("result = " + result);

        /**
         * getMethods获取类中以及父类的pulbic方法
         * getDeclaredMethods获取类中的所以方法
         */
        Method[] methods = mCls.getMethods();
        for (Method method : methods) {
            System.out.println("method = " + method);
        }
        System.out.println("===========================" );

        Method[] declaredMethods = mCls.getDeclaredMethods();
        for (Method declaredMethod : declaredMethods) {
            System.out.println("declaredMethod = " + declaredMethod);
        }
    }
}

结果截图:

1.

2.

类中的成员变量获取不在细说,通过再次整理,开发中java中的反射轻易不要,除非非用不可。

三、练习一下自己定义一个框架:

1.配置文件

beanName=com.bank.pojo.DiyPojo
mothedName=Study

2.测试类

public class DiyPojo {

    private void Study(String name){

        System.out.println(name+"周末还在努力工作....");
    }
}

3.测试方法

public class DiySpring {
    public String ConfigName;

    public void actionWorking(String name) throws IOException, ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {
        //1.获取类加载器
        InputStream in = DiySpring.class.getClassLoader().getResourceAsStream(ConfigName);
        //2.读取内容
        Properties pp = new Properties();
        pp.load(in);
        System.out.println("pp = " + pp);

        String beanName = pp.getProperty("beanName");
        String mothedName = pp.getProperty("mothedName");
        //3.执行方法
        Class<?> bCls = Class.forName(beanName);
        Object instance = bCls.getDeclaredConstructor().newInstance();

        Method method = bCls.getDeclaredMethod(mothedName,String.class);
        //暴力反射
        method.setAccessible(true);
        method.invoke(instance,name);

    }

    public static void main(String[] args) throws NoSuchMethodException, IOException, InstantiationException, IllegalAccessException, InvocationTargetException, ClassNotFoundException {
        DiySpring diySpring = new DiySpring();
        diySpring.ConfigName="config.properties";
        diySpring.actionWorking("狗子");
    }
}

简单的创建一个类,项目启动的时候可以把要加载的内容这样编辑,比如提前查库加载一些通用的信息、数据库的配置信息等

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值