日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

09、策略模式

發(fā)布時間:2023/11/30 编程问答 24 豆豆
生活随笔 收集整理的這篇文章主要介紹了 09、策略模式 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

2019獨角獸企業(yè)重金招聘Python工程師標(biāo)準(zhǔn)>>>

策略模式與工廠模式最大的區(qū)別在于,策略模式注重的是對算法的維護,也可以理解為對算法的封裝。而工廠模式,則只是負(fù)責(zé)創(chuàng)建類,在剛接觸策略模式時候,往往與工廠模式容易產(chǎn)生混淆。 官方對策略模式的解釋: 它定義了算法家族,分別封裝起來,讓他們之間可以互換,此模式,讓算法的變化不會影響到使用算法的客戶。
從此模式開始,每次總結(jié)的時候畫出一個UML圖。
此例子結(jié)合商場搞活動銷售活動,商品價格打折、以及返價活動。 任何一種活動,最終都要有一個計算結(jié)果的方法,所以對此方法進行抽象:
  • public interface PriceCalculate {
  • public abstract double getFinalPrice();
  • }
  • 然后對其進行實現(xiàn),分別為不搞活動,折扣,返現(xiàn)活動,分別如下:
  • public class NormalPrice implements PriceCalculate {
  • private double finalPrice = 0d;
  • public double getFinalPrice() {
  • // TODO Auto-generated method stub
  • return finalPrice;
  • }
  • public NormalPrice(double sourcePrice){
  • this.finalPrice = sourcePrice;
  • }
  • }
  • 然后是折扣活動:
  • public class DebetPrice implements PriceCalculate {
  • private double finalPrice = 0d;
  • @Override
  • public double getFinalPrice() {
  • return finalPrice;
  • }
  • public DebetPrice(double sourcePrice,double debet){
  • this.finalPrice = Calculate.mul(sourcePrice, debet);
  • }
  • }
  • Calculate為工具類,具體代碼在最后。 然后是折現(xiàn)活動:
  • public class ReturnPrice implements PriceCalculate {
  • private double finalPrice = 0d;
  • @Override
  • public double getFinalPrice() {
  • // TODO Auto-generated method stub
  • return finalPrice;
  • }
  • /**滿多少價反錢活動
  • * @param sourcePrice 原價
  • * @param conditionPrice 返現(xiàn)金消費額度
  • * @param returnPrice 返現(xiàn)金力度
  • */
  • public ReturnPrice(double sourcePrice,double conditionPrice,double returnPrice){
  • this.finalPrice = sourcePrice;
  • if( sourcePrice >= conditionPrice ){
  • double times = Math.floor(Calculate.div(sourcePrice, conditionPrice)) ;
  • int count = times>=1? (int)times:0;
  • while(count-->0){
  • this.finalPrice = Calculate.sub(sourcePrice,returnPrice);
  • }
  • }
  • }
  • }


  • 其中的Calculate為工具類,具體如下:
  • package com.yp.learn.util;
  • import java.math.BigDecimal;
  • public class Calculate {
  • // 默認(rèn)除法運算精度
  • private static final int DEF_DIV_SCALE = 10;
  • private Calculate(){};
  • /**精確 加法運算
  • * @param d1 被加數(shù)
  • * @param d2 加數(shù)
  • * @return 和
  • */
  • public static double add(double d1,double d2){
  • BigDecimal b1= new BigDecimal(Double.toString(d1));
  • BigDecimal b2= new BigDecimal(Double.toString(d2));
  • return b1.add(b2).doubleValue();
  • }
  • /**
  • * 提供精確的減法運算。
  • * @param v1 被減數(shù)
  • * @param v2 減數(shù)
  • * @return 兩個參數(shù)的差
  • */
  • public static double sub(double v1, double v2) {
  • BigDecimal b1 = new BigDecimal(Double.toString(v1));
  • BigDecimal b2 = new BigDecimal(Double.toString(v2));
  • return b1.subtract(b2).doubleValue();
  • }
  • /**
  • * 提供精確的乘法運算。
  • * @param v1 被乘數(shù)
  • * @param v2 乘數(shù)
  • * @return 兩個參數(shù)的積
  • */
  • public static double mul(double v1, double v2) {
  • BigDecimal b1 = new BigDecimal(Double.toString(v1));
  • BigDecimal b2 = new BigDecimal(Double.toString(v2));
  • return b1.multiply(b2).doubleValue();
  • }
  • /**
  • * 提供(相對)精確的除法運算,當(dāng)發(fā)生除不盡的情況時,精確到 小數(shù)點以后10位,以后的數(shù)字四舍五入。
  • * @param v1 被除數(shù)
  • * @param v2 除數(shù)
  • * @return 兩個參數(shù)的商
  • */
  • public static double div(double v1, double v2) {
  • return div(v1, v2, DEF_DIV_SCALE);
  • }
  • /**
  • * 提供(相對)精確的除法運算。當(dāng)發(fā)生除不盡的情況時,由scale參數(shù)指 定精度,以后的數(shù)字四舍五入。
  • * @param v1 被除數(shù)
  • * @param v2 除數(shù)
  • * @param scale 表示表示需要精確到小數(shù)點以后幾位。
  • * @return 兩個參數(shù)的商
  • */
  • public static double div(double v1, double v2, int scale) {
  • if (scale < 0) {
  • throw new IllegalArgumentException(
  • "The scale must be a positive integer or zero");
  • }
  • BigDecimal b1 = new BigDecimal(Double.toString(v1));
  • BigDecimal b2 = new BigDecimal(Double.toString(v2));
  • return b1.divide(b2, scale, BigDecimal.ROUND_HALF_UP).doubleValue();
  • }
  • }
  • 然后策略模式的核心出來了,幾種類都已經(jīng)實現(xiàn)類,并且都有算法,策略模式要做的,就是 對這個抽象出來的 算法進行 維護,如下:
  • public class PriceCalculateContext {
  • PriceCalculate cal = null;
  • /**無活動情況
  • * @param sourcePrice
  • */
  • public PriceCalculateContext(double sourcePrice){
  • cal = new NormalPrice(sourcePrice);
  • }
  • /**打折活動
  • * @param sourcePrice 原價
  • * @param debet 打折力度
  • */
  • public PriceCalculateContext(double sourcePrice,double debet){
  • cal = new DebetPrice(sourcePrice,debet);
  • }
  • /**返現(xiàn)活動
  • * @param sourcePrice 原價
  • * @param conditionPrice 返現(xiàn)所需滿足額度
  • * @param returnPrice 返現(xiàn)力度
  • */
  • public PriceCalculateContext(double sourcePrice,double conditionPrice,double returnPrice){
  • cal = new ReturnPrice(sourcePrice,conditionPrice,returnPrice);
  • }
  • public double getResult() {
  • return cal.getFinalPrice();
  • }
  • }
  • 與之前的工廠模式相比較,策略模式并沒有提供創(chuàng)建運算類的工廠類,而只是將這些運算類維護在了PriceCalculateContext類中,并且此類中提供了方法getResult(),此方法所調(diào)用的剛好是算法接口。那么現(xiàn)在,客戶端的代碼就非常的清晰了:
  • public class Start {
  • public static void main(String[] args) {
  • PriceCalculateContext p = new PriceCalculateContext(100d);
  • System.out.println(p.getResult());
  • p = new PriceCalculateContext(122.2d, 100d, 15d);
  • System.out.println(p.getResult());
  • }
  • }
  • 通過構(gòu)造價格計算維護類來計算所得的最終結(jié)果,計算的具體形式完全對客戶端屏蔽。策略模式最明顯的就是對每種策略所實現(xiàn)的算法進行了封裝,在本例中,就是 PriceCalculateContext的getResult的方法,在后續(xù),可以說如果需要新增新的算法,那么我只需要新增新的算法類,然后在PriceCalculateContext增加相應(yīng)的映射即可。在客戶端只需要依據(jù)不同的參數(shù)進行初始化,然后調(diào)用的方法不用發(fā)生任何改變。 UML圖如下:
    從類圖上也可以看到,客戶端的代碼只關(guān)聯(lián)PriceCalculateContext類,解耦很成功。
    還是強調(diào)一點,策略模式注重對策略的封裝。


    總結(jié)分析: 1、比較工廠模式,此模式通過增加算法維護類(PriceCalculateContext),對所有的算法進行封裝,并且在客戶端代碼中,只有此類創(chuàng)建和使用。 2、當(dāng)新增類的時候,需要算法維護類中修改代碼,相當(dāng)于需求和實現(xiàn)做映射關(guān)系。即客戶端代碼依然沒有轉(zhuǎn)移條件判斷。



    來自為知筆記(Wiz)

    轉(zhuǎn)載于:https://my.oschina.net/u/1182369/blog/406571

    總結(jié)

    以上是生活随笔為你收集整理的09、策略模式的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。