策略模式应用场景

Posted aspirant

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了策略模式应用场景相关的知识,希望对你有一定的参考价值。

有个大神写的很好:

参考:设计模式学习笔记(四:策略模式)

参考:设计模式学习笔记(二:观察者模式)

参考:设计模式学习笔记-代理模式

一、策略模式:
 (1)解决场景:
某个功能有多个方案可以实现,要达到某个目的,需要根据具体的实际情况,选择合适的方法,
 (2)如何实现:
分为两个层次
 (a) 环境类
 环境类负责接收用户的请求,并根据实际情况把相应的请求委托给一组策略类中的一个;

 (b) 一组策略类
  一组封装了具体的实现类的算法,并负责具体的计算过程

(3)关键类图:

 技术分享图片

 首先定义策略类的接口: 

public interface GameStrategy {
 
     public void goldCoin();
 
}

其次 实现一组策略类:

public class normalStrategy implements GameStrategy {   
                                                        
    @Override                                           
    public void goldCoin() {                            
        //                                              
        System.out.println("普通玩家没有折扣");                 
    }                                                   
}       

public class advancedStrategy implements GameStrategy {

    @Override
    public void goldCoin() {
        // TODO Auto-generated method stub
        System.out.println("高级会员9折优惠");
    }
}

环境类的实现:

public class Context {                                
  //持有一个Strategy的引用                                   
    private GameStrategy mGameStrategy;               
                                                      
    // 构造函数                                           
    public Context(GameStrategy strategy) {           
        this.mGameStrategy = strategy;                
    }                                                 
                                                      
    public void setStrategy(GameStrategy strategy) {  
        this.mGameStrategy = strategy;                
    }                                                 
                                                      
    public void goldCoin() {                          
        this.mGameStrategy.goldCoin();                
    }                                                 
}        

最后根据不同的情况进行调用:

public class main {                                          
                                                             
    public static void main(String[] args) {                 
        //普通玩家策略                                             
        Context context = new Context(new normalStrategy()); 
        context.goldCoin();                                  
        //高级玩家策略                                             
        context.setStrategy(new advancedStrategy());         
        context.goldCoin();                                 
                                     
    }                                                        
}   

 二、观察者模式

(1)解决场景:
  (a) 对一个对象状态的更新,需要其他对象同步更新
  (b) 对象仅需要将自己的更新通知给其他对象而不需要知道其他对象的细节
观察者模式,又称为发布订阅模式,它的特点:
  (a) subject 和 observer之间是松耦合的,各自独立实现,
  (b) subject在发送广播通知的时候,不需要指定具体的observer,observer可以自行决定是否要订阅
  (c) 遵循常用设计原则:高内聚,低耦合
(2)如何实现:

关键类图:

技术分享图片

 定义观察者接口: 

public interface Observer {
     void update(String message,String name);
 }

实现观察者:

                                                                  
public class Bianyi1 implements Observer {                             
    //定义姓名                                                             
    private String bname = "张昊天";                                      
    @Override                                                          
    public void update(String message,String name) {                   
        System.out.println(bname+":"+name+"那里有新情况:"+ message);         
    }                                                                  
}                                                                     
                                                                
public class Bianyi2 implements Observer {                             
    //定义姓名                                                             
    private String bname = "石破天";                                      
    @Override                                                          
    public void update(String message,String name) {                   
        System.out.println(bname+":"+name+"那里有新情况:"+ message);         
    }                                                                  
}   

定义目标接口:

public interface Huairen {                  
    //添加便衣观察者                               
    void addObserver(Observer observer);    
    //移除便衣观察者                               
    void removeObserver(Observer observer); 
    //通知观察者                                 
    void notice(String message);            
} 

两个实现目标的类:

import java.util.*;                                                          
/**                                                                          
 * 嫌犯大熊                                                                      
 */                                                                          
public class XianFan1 implements Huairen {                                   
    //别称                                                                     
    private String name = "大熊";                                              
    //定义观察者集合                                                                
    private List<Observer> observerList = new ArrayList<Observer>();         
    //增加观察者                                                                  
    @Override                                                                
    public void addObserver(Observer observer) {                             
        if(!observerList.contains(observer)){                                
            observerList.add(observer);                                      
        }                                                                    
    }                                                                        
    //移除观察者                                                                  
    @Override                                                                
    public void removeObserver(Observer observer) {                          
        if(observerList.contains(observer)){                                 
            observerList.remove(observer);                                   
        }                                                                    
    }                                                                        
    //通知观察者                                                                  
    @Override                                                                
    public void notice(String message) {                                     
        for(Observer observer:observerList){                                 
            observer.update(message,name);                                   
        }                                                                    
    }                                                                        
}                                                                            
                                                                             
import java.util.*;                                                          
/**                                                                          
 * 嫌犯黑狗                                                                      
 */                                                                          
public class XianFan2 implements Huairen {                                   
    //别称                                                                     
    private String name = "黑狗";                                              
    //定义观察者集合                                                                
    private List<Observer> observerList = new ArrayList<Observer>();         
    //增加观察者                                                                  
    @Override                                                                
    public void addObserver(Observer observer) {                             
        if(!observerList.contains(observer)){                                
            observerList.add(observer);                                      
        }                                                                    
    }                                                                        
    //移除观察者                                                                  
    @Override                                                                
    public void removeObserver(Observer observer) {                          
        if(observerList.contains(observer)){                                 
            observerList.remove(observer);                                   
        }                                                                    
    }                                                                        
    //通知观察者                                                                  
    @Override                                                                
    public void notice(String message) {                                     
        for(Observer observer:observerList){                                 
            observer.update(message,name);                                   
        }                                                                    
    }                                                                        
}  

观察者根据目标进行调用:

public class Clienter {                           
    public static void main(String[] args) {      
        //定义两个嫌犯                                  
        Huairen xf1 = new XianFan1();             
        Huairen xf2 = new XianFan2();             
        //定义三个观察便衣警察                              
        Observer o1 = new Bianyi1();              
        Observer o2 = new Bianyi2();          
        //为嫌犯增加观察便衣                               
        xf1.addObserver(o1);                      
        xf1.addObserver(o2);                      
        xf2.addObserver(o1);                      
        xf2.addObserver(o3);                      
        //定义嫌犯1的情况                                
        String message1 = "又卖了一批货";               
        String message2 = "老大要下来视察了";             
        xf1.notice(message1);                     
        xf2.notice(message2);                     
    }                                             
}       

 

三、代理模式:
(1)解决场景:
    (a) 当我们想要隐藏某个类时,可以为其提供代理类

  (b) 当一个类需要对不同的调用者提供不同的调用权限时,可以使用代理类来实现

  (c) 当我们要扩展某个类的某个功能时,可以使用代理模式,在代理类中进行简单扩展
(2) 如何实现:
  (a) 代理类与委托类实现同一接口
  (b) 在委托类中实现功能,在代理类的方法中中引用委托类的同名方法
  (c) 外部类调用委托类某个方法时,直接以接口指向代理类的实例,这正是代理的意义所在:屏蔽。

(3) 类图:

技术分享图片

 (a) 抽象的主题:

public interface Moveable {
    void move()  throws Exception;
}

(b)真实主题:

public class Car implements Moveable {
    public void move() throws Exception {
        Thread.sleep(new Random().nextInt(1000));
        System.out.println("汽车行驶中…");
    }
}

(c) 事务处理器:

public class TimeHandler implements InvocationHandler {
    private Object target;
   
    public TimeHandler(Object target) {
        super();
        this.target = target;
    }
 
    /**
     * 参数:
     *proxy 被代理的对象
     *method 被代理对象的方法
     *args 方法的参数
     * 返回:
     *Object 方法返回值
     */
    public Object invoke(Object proxy, Method method, Object[] args)
            throws Throwable {
        long startTime = System.currentTimeMillis();
        System.out.println("汽车开始行驶…");
        method.invoke(target, args);
        long stopTime = System.currentTimeMillis();
        System.out.println("汽车结束行驶…汽车行驶时间:" + (stopTime - startTime) + "毫秒!");
        return null;
    }
 
}

(d) 调用:

public class Test {
    public static void main(String[] args) throws Exception{
        Car car = new Car();
        InvocationHandler h = new TimeHandler(car);
        Class<?> cls = car.getClass();
        /**
         *loader 类加载器
         *interfaces 实现接口
         *h InvocationHandler
         */
        Moveable m = (Moveable) Proxy.newProxyInstance(cls.getClassLoader(),cls.getInterfaces(), h);
        m.move();
    }

 

以上是关于策略模式应用场景的主要内容,如果未能解决你的问题,请参考以下文章

设计模式 - 应用场景:模板方法模式 + 策略模式 + Lambda

设计模式策略模式 ( 简介 | 适用场景 | 优缺点 | 代码示例 )

设计模式之策略模式

设计模式之策略模式与责任链模式详解和应用

策略模式

模板方法模式策略模式 的 联系区别和应用场景