• 加载配置文件内容利用反射动态创建对象和调用方法(开闭原则的体现)


    反射的应用:根据配置文件来创建对象和调用方法

    需求:1,根据配置文件re.properties 指定的信息,创建对象并调用方法
    classfullpath=src.com.liu.Cat
    method=hi
    即通过外部文件配置,在不修改源码的情况下,来控制程序,
    当method=hi变成了method=cry时,不修改代码也可以正常运行达到我们想要的效果
    (这符合设计模式的 ocp 原则即开闭原则对修改权限进行关闭,对拓展功能进行开放

    1.传统的做法

    通过传统的 new 一个对象 然后通过new出的对象点方法来调用方法
    Cat cat = new Cat();
    cat.hi();
    弊端: 当想要调用的方法发生改变时例如此刻我想调用cry()方法不再调用hi()方法,就必须要把cat.hi()方法修改成cat.cry()。这修改了源码,不符合开闭原则

    2.读取配置文件,通过配置文件里的路径来new一个对象
        Properties properties = new Properties();
        properties.load(new FileInputStream("src/com/liu/re.properties"));
        String classfullpath = properties.get("classfullpath").toString();
        String methodName = properties.get("method").toString();
        System.out.println("classfullpath="+classfullpath);
        System.out.println("method="+methodName);
        // 传统的方式不行
        new classfullpath();//classfullpath 是String 类型,不是全路径
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8

    可以看到下图中编译不通过因为classfullpath 是String 类型,不是全路径在这里插入图片描述

    3.通过反射来解决2中出现的这个问题
        //三,使用反射机制来解决
        Class cls = Class.forName(classfullpath);
        Object o = cls.newInstance();
        System.out.println("o 的运行时类型= "+o.getClass());
        Method method1 = cls.getMethod(methodName);
        //通过method1调用方法,即通过方法对象调用方法
        method1.invoke(o);
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    运行结果如下:在这里插入图片描述
    当修改re.properties,把method变成cry时
    在这里插入图片描述
    运行结果:
    在这里插入图片描述
    可以看出,这实现了在不修改源码的情况下只需要修改配置文件,就能实现当方法改变时,程序也能跟着改变

    4.文件夹结构与代码

    在这里插入图片描述

    Cat.java

    package src.com.liu;
    
    public class Cat {
        private String name = "招财猫";
        public void hi(){
            System.out.println("hi"+name);
        }
        public void cry(){
            System.out.println(name+"喵喵叫");
        }
    }
    
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    re.properties

    classfullpath=src.com.liu.Cat
    method=hi
    #method=cry
    
    • 1
    • 2
    • 3

    ReflectionQuestion.java

    package src.com.liu.reflection.question;
    
    import src.com.liu.Cat;
    
    import java.io.FileInputStream;
    import java.io.FileNotFoundException;
    import java.io.IOException;
    import java.lang.reflect.InvocationTargetException;
    import java.lang.reflect.Method;
    import java.util.Properties;
    
    public class ReflectionQuestion {
        public static void main(String[] args) throws IOException, ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {
            //根据配置文件 re.properties 指定信息,创建Cat 对象并调取方法hi
    
            //一,传统的方法 new 对象 -》 方法调用
            Cat cat = new Cat();
            cat.hi();
    
            // 二,. 使用 Properties 类,可以读取配置文件
            Properties properties = new Properties();
            properties.load(new FileInputStream("src/com/liu/re.properties"));
            String classfullpath = properties.get("classfullpath").toString();
            String methodName = properties.get("method").toString();
            System.out.println("classfullpath="+classfullpath);
            System.out.println("method="+methodName);
            // 传统的方式不行
            //new classfullpath();//classfullpath 是String 类型,不是全路径
    
            //三,使用反射机制来解决
            Class cls = Class.forName(classfullpath);
            Object o = cls.newInstance();
            System.out.println("o 的运行时类型= "+o.getClass());
            Method method1 = cls.getMethod(methodName);
            //通过method1调用方法,即通过方法对象调用方法
            method1.invoke(o);
            //如果是传统的做法我要求调用 cry方法,而不是调用 hi方法,
            //Cat cat = new Cat(); cat.hi();====> cat.cry();需修改源码
    
            //使用反射的 做法是: 把配置文件re.properties 的 method=hi,改成method=cry就可以了,
            //只修改配置文件,不修改源代码
    
    
        }
    
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
  • 相关阅读:
    决策树处理UNSW-NB15数据集
    内存操作函数(memcpy、memmove、memset、memcmp)---- C语言
    什么是MapReduce
    【OpenCV】Chapter8.形态学图像处理
    数值微分比较
    Maven基础知识【基本概念、项目结构、依赖管理、生命周期与插件】
    10.20复习
    小红书怎么看关键词排名?如何提升笔记自然搜索排名
    HCIA使用DHCP配置eNSP,给路由器加权限并且加密
    用keras框架训练模型,画loss曲线
  • 原文地址:https://blog.csdn.net/weixin_43225966/article/details/128052720