策略、工廠模式融合 InitializingBean

策略细燎、工廠模式融合 InitializingBean

策略缝呕、工廠模式分別是什么

策略模式

策略模式是將不同的算法封裝成一個對象澳窑,這些不同的算法從一個抽象類或者一個接口中派生出來,客戶端持有一個抽象的策略的引用岳颇,這樣客戶端就能動態(tài)的切換不同的策略

工廠模式

工廠模式又分為簡單工廠和抽象工廠和工廠模式 照捡,這些工廠是為了創(chuàng)建對象而出現的,工廠模式創(chuàng)建不同的單個對象话侧,而抽象工廠是為了創(chuàng)建不同的一些列的對象或者操作

策略+工廠解決的痛點是什么

結合工廠模式通過不同的類型栗精,生產不同的對象和策略模式根據不同的對象,執(zhí)行相同方法內的不同行為瞻鹏,來消滅大量的 if else 或 switch case ...悲立,增強代碼的可擴展性,便于代碼質量維護

上代碼

代碼基礎:springboot 2.3.2

這里以 Animal 為策略的接口新博,Cat薪夕、Dog為策略具體的實現

public interface Animal {
    void eat(String str);
}

/**
 * @Author charmsongo
 * @Create 2020/8/6 22:22
 * @Description 實現 InitializingBean ,便于 spring 容器時赫悄,初始化一次 afterPropertiesSet
 *              在 afterPropertiesSet 方法中把當前策略具體實現類注冊到策略中維護的 map 中
 */
@Component
public class Cat implements Animal, InitializingBean {
    private static final Logger logger = LoggerFactory.getLogger(Cat.class);

    @Override
    public void eat(String str) {
        logger.info("cat eat yu, {}", str);
    }
    
    /**
     * 注冊到策略模式維護的集合中
     * @throws Exception
     */
    @Override
    public void afterPropertiesSet() throws Exception {
        AnimalContext.registerService(AnimalEnum.CAT.getCode(),this);
    }
}

/**
 * @Author charmsongo
 * @Create 2020/8/6 22:24
 * @Description 實現 InitializingBean 原献,便于 spring 容器時馏慨,初始化一次 afterPropertiesSet
 *              在 afterPropertiesSet 方法中把當前策略具體實現類注冊到策略中維護的 map 中
 */
@Component
public class Dog implements Animal, InitializingBean {
    private static final Logger logger = LoggerFactory.getLogger(Dog.class);

    @Override
    public void eat(String str) {
        logger.info("dog eat gutou, {}", str);
    }

    /**
     * 注冊到策略模式維護的集合中
     * @throws Exception
     */
    @Override
    public void afterPropertiesSet() throws Exception {
        AnimalContext.registerService(AnimalEnum.DOG.getCode(),this);
    }
}

這里用枚舉來作為 map 的 key,此處直接使用姑隅,不用過多關注

public enum AnimalEnum {

    CAT("01", "cat","貓"),
    DOG("02", "dog","狗");

    private String code;
    private String shortCode;
    private String msg;

    AnimalEnum(String code, String shortCode, String msg) {
        this.code = code;
        this.shortCode = shortCode;
        this.msg = msg;
    }

    public String getShortCode() {
        return shortCode;
    }

    public void setShortCode(String shortCode) {
        this.shortCode = shortCode;
    }

    public String getCode() {
        return code;
    }

    public void setCode(String code) {
        this.code = code;
    }

    public String getMsg() {
        return msg;
    }

    public void setMsg(String msg) {
        this.msg = msg;
    }

    @Override
    public String toString() {
        return "AnimalEnum{" +
                "code='" + code + '\'' +
                ", shortCode='" + shortCode + '\'' +
                ", msg='" + msg + '\'' +
                '}';
    }

    public static boolean isValid(String code) {
        for (AnimalEnum value : AnimalEnum.values()) {
            if (value.getCode().equals(code)) {
                return true;
            }
        }
        return false;
    }
}

策略+工廠模式具體的操作

/**
 * @Author charmsongo
 * @Create 2020/8/6 22:28
 * @Description 策略+工廠
 */
public class AnimalContext {
    private static final Logger logger = LoggerFactory.getLogger(AnimalContext.class);
    private static Map<String, Animal> animalMap = new HashMap<String, Animal>();
    private Animal animal;

    public AnimalContext(String type) throws Exception {
        //此處判空写隶,沒有可以拋異常
        if (StringUtils.isEmpty(type) || !animalMap.containsKey(type)) {
            logger.error("type is error.");
            throw new Exception("type is error.");
        }
        animal = animalMap.get(type);
    }

    /**
     * 策略 eat 方法
     * @param str
     */
    public void eat(String str) {
        animal.eat(str);
    }

    /**
     * 策略注冊方法
     * @param type
     * @param animal
     */
    public static void registerService(String type, Animal animal) {
        animalMap.put(type, animal);
    }
}

測試

咱們 web 應用一般都是以服務的方式使用的,這里也以服務的方式測試

新加一個 Controller 和 Request

@RestController
public class StrategyController {
    /**
     * http://localhost:8080/hello?code=01
     * @param animalRequest
     */
    @GetMapping("/hello")
    public void hello(AnimalRequest animalRequest) {
        try {
            AnimalContext animalContext  = new AnimalContext(animalRequest.getCode());
            animalContext.eat("哈哈");
            animalContext.run("喜喜");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}


public class AnimalRequest implements Serializable {
    private static final long serialVersionUID = 3784925575397162170L;

    private String code;
    // 省去 set讲仰、get慕趴、toString 方法
}

啟動 SpringBoot 工程的 Application 主類

瀏覽器訪問 http://localhost:8080/hello?code=01

然后查看 IDE 控制臺,出現 cat eat yu, 哈哈 即為成功鄙陡!

2020-10-13 22:38:28.712  INFO 12584 --- [nio-8080-exec-2] cn.songo.strategydemo.service.impl.Cat   : cat eat yu, 哈哈

代碼詳情可參考源碼冕房,github:https://github.com/charmsongo/songo-code-samples/tree/master/strategydemo

如果有哪些不對的地方煩請指認,先行感謝

?著作權歸作者所有,轉載或內容合作請聯系作者
  • 序言:七十年代末趁矾,一起剝皮案震驚了整個濱河市耙册,隨后出現的幾起案子,更是在濱河造成了極大的恐慌愈魏,老刑警劉巖觅玻,帶你破解...
    沈念sama閱讀 218,122評論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現場離奇詭異培漏,居然都是意外死亡溪厘,警方通過查閱死者的電腦和手機,發(fā)現死者居然都...
    沈念sama閱讀 93,070評論 3 395
  • 文/潘曉璐 我一進店門牌柄,熙熙樓的掌柜王于貴愁眉苦臉地迎上來畸悬,“玉大人,你說我怎么就攤上這事珊佣√;拢” “怎么了?”我有些...
    開封第一講書人閱讀 164,491評論 0 354
  • 文/不壞的土叔 我叫張陵咒锻,是天一觀的道長冷冗。 經常有香客問我,道長惑艇,這世上最難降的妖魔是什么蒿辙? 我笑而不...
    開封第一講書人閱讀 58,636評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮滨巴,結果婚禮上思灌,老公的妹妹穿的比我還像新娘。我一直安慰自己恭取,他們只是感情好泰偿,可當我...
    茶點故事閱讀 67,676評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蜈垮,像睡著了一般耗跛。 火紅的嫁衣襯著肌膚如雪裕照。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,541評論 1 305
  • 那天课兄,我揣著相機與錄音牍氛,去河邊找鬼。 笑死烟阐,一個胖子當著我的面吹牛,可吹牛的內容都是我干的紊扬。 我是一名探鬼主播蜒茄,決...
    沈念sama閱讀 40,292評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼餐屎!你這毒婦竟也來了檀葛?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 39,211評論 0 276
  • 序言:老撾萬榮一對情侶失蹤腹缩,失蹤者是張志新(化名)和其女友劉穎屿聋,沒想到半個月后,有當地人在樹林里發(fā)現了一具尸體藏鹊,經...
    沈念sama閱讀 45,655評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡润讥,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 37,846評論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現自己被綠了盘寡。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片楚殿。...
    茶點故事閱讀 39,965評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖竿痰,靈堂內的尸體忽然破棺而出脆粥,到底是詐尸還是另有隱情,我是刑警寧澤影涉,帶...
    沈念sama閱讀 35,684評論 5 347
  • 正文 年R本政府宣布变隔,位于F島的核電站,受9級特大地震影響蟹倾,放射性物質發(fā)生泄漏匣缘。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,295評論 3 329
  • 文/蒙蒙 一喊式、第九天 我趴在偏房一處隱蔽的房頂上張望孵户。 院中可真熱鬧,春花似錦岔留、人聲如沸夏哭。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,894評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽竖配。三九已至何址,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間进胯,已是汗流浹背用爪。 一陣腳步聲響...
    開封第一講書人閱讀 33,012評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留胁镐,地道東北人偎血。 一個月前我還...
    沈念sama閱讀 48,126評論 3 370
  • 正文 我出身青樓,卻偏偏與公主長得像盯漂,于是被迫代替她去往敵國和親颇玷。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 44,914評論 2 355