美文网首页
策略(Strategy)模式+工厂(Factory)模式

策略(Strategy)模式+工厂(Factory)模式

作者: 林亚希 | 来源:发表于2022-08-02 15:04 被阅读0次

    策略(Strategy)模式+工厂(Factory)模式

    描述

    策略模式很多时候都伴随着工厂模式一起使用。
    比较拗口的说明

    • 抽象策略(Strategy)类:公共接口,各种不同的算法以不同的方式实现这个接口,环境角色使用这个接口调用不同的算法,一般使用接口或抽象类实现。
    • 具体策略(Concrete Strategy)类:实现了抽象策略定义的接口,提供具体的算法实现。
    • 环境(Context)类:持有一个策略类的引用,最终给客户端调用。

    从实际使用场景中更快的来理解。

    场景

    • 不同等级的会员享受不同等级的服务。
    // 这个是抽象策略
    public abstract class ActivityAbstractExecutor {
    
        public abstract void execute();
    
    }
    
    //黄金会员执行业务逻辑
    @Service("goldMemberExecutor")
    public class GoldMemberExecutor extends ActivityAbstractExecutor {
        @Override
        public void execute() {
            //业务代码
            System.out.println("这里是黄金会员");
        }
    }
    
    //白银会员执行业务逻辑
    @Service("silverMemberExecutor")
    public class SilverMemberExecutor extends ActivityAbstractExecutor {
        @Override
        public void execute() {
            //业务代码
            System.out.println("这里是白银会员");
        }
    }
    
    
    // 这是个枚举类,包含所有的会员类型
    public enum AgentActivityEnum {
    
        GOLD_ACTIVITY(1L, "goldMemberExecutor", "黄金会员活动"),
        SILVER_ACTIVITY(2L, "silverMemberExecutor", "白银会员活动");
        private final Long activityId;
        private final String beanName;
        private final String desc;
        AgentActivityEnum(Long activityId, String beanName, String desc) {
            this.beanName = beanName;
            this.activityId = activityId;
            this.desc = desc;
        }
        public Long getActivityId() {
            return activityId;
        }
        public String getBeanName() {
            return beanName;
        }
        public String getDesc() {
            return desc;
        }
    }
    
    // 这个是工厂启动时候扫入所有的会员服务
    @Service
    public class ActivityFactory {
        //所有的会员服务类实例都存到一个map中。key为会员ID,value为某个会员的bean名称
        private static final Map<Long, String> beanNames = new ConcurrentHashMap<>();
        static {
            AgentActivityEnum[] activityEnums = AgentActivityEnum.values();
            for (AgentActivityEnum activityEnum : activityEnums) {
                beanNames.put(activityEnum.getActivityId(), activityEnum.getBeanName());
            }
        }
        //通过Map注入,通过 spring bean 的名称作为key动态获取对应实例 这个地方可以学习下,Spring在注入的时候是可以根据类型注入的。
        @Autowired
        private Map<String, ActivityAbstractExecutor> executorMap;
        //工厂层执行器
        public void execute(Long activityId) {
            String beanName = beanNames.get(activityId);
            if (null == beanName) {
                return;
            }
            //决定最终走哪个类的执行器
            ActivityAbstractExecutor executor = executorMap.get(beanName);
            if (executor == null) {
                return;
            }
            executor.execute();
        }
    }
    
    // 这个是工厂启动时候扫入所有的会员服务
    @RestController
    public class MainTest {
    
        @Autowired
        private ActivityFactory activityFactory;
        @GetMapping("/strategy/test")
        public String get(){
            activityFactory.execute(AgentActivityEnum.GOLD_ACTIVITY.getActivityId());
            activityFactory.execute(AgentActivityEnum.SILVER_ACTIVITY.getActivityId());
            return "123123123";
        }
    }
    

    在编写业务代码中经常可以使用的设计模式

    相关文章

      网友评论

          本文标题:策略(Strategy)模式+工厂(Factory)模式

          本文链接:https://www.haomeiwen.com/subject/qehjwrtx.html