0
点赞
收藏
分享

微信扫一扫

4、行为型模式(设计模式)

WikongGuan 2022-02-08 阅读 81

行为型模式

1、行为模式关注点"怎样运行对象/类",所以我们关注类/对象的运行时流程控制。
2、行为模式用于描述程序在运行时复杂的流程控制,描述多个类或对象之间怎样相互协作共同完成单个对象都无法单独完成的任务,它涉及算法与对象间的职责分配。
3、行为型模式分为类行为模式和对象行为模式,前者采用继承机制来在类间分配行为,后者采用组合或聚合在对象间分配行为。由于组合关系或聚合关系比继承关系耦合度更低,满足“合成复用原则”,所以对象行为模式比类行为模式具有更大的灵活性。

未命名文件 82.png

模板方法模式:父类定义算法骨架,某些实现放子类
策略模式:每种算法独立封装,根据不同情况使用不同算法策略
状态模式:每种状态独立封装,不同状态内部封装了不同行为
命令模式:将一个请求封装为一个对象,使发出请求的责任和执行请求的责任分割开
责任链模式:所有处理者封装为链式结构,依次调用
备忘录模式:把核心信息抽取出来,可以进行保存
解释器模式:定义语法解析规则
观察者模式:维护多个观察者依赖,状态变化通知所有观察者
中介者模式:取消类/对象的直接调用关系,使用中介者维护
迭代器模式:定义集合数据的遍历规则
访问者模式:分离对象结构与元素的执行算法

除了模板方法模式和解释器模式是类行为模式,其他的全部属于对象行为模式

模板方法模式

在模板方法模式中,一个抽象类公开定义了执行它的方法的方式模板。它的子类可以按需要重写方法实现,但调用将以抽象类中定义的方式进行。
模板方法包含两个角色:
抽象类/抽象模板
具体子类/具体实现

例子

做饭都要经历加热,添加食材,添加调料,翻炒,出锅,这是一个模板,有方法是固定的不需要改变的,如加热,翻炒,出锅,这些就可以定义到模板里,加什么食材,加什么调料,这些是不一定的,可以随时改变,就在子类中实现。
package com.example.design.template;

/**
 * 1、定义模板
 */
public abstract class CookTemplate {
    /**
     * 定义算法:定义好了模板
     * 父类可以实现某些步骤
     * 留一些关键核心给子类
     */
    public void cook(){
        //定义算法步骤
        heating();
        addfood();
        addsalt();
        stirfry();
        end();
    }
    //加热方法
    public void heating(){
        System.out.println("开火。。。。。。。。");
    }
    //添加实物
    public abstract void addfood();
    //加盐
    public abstract void addsalt();
    //翻炒
    public void stirfry(){
        System.out.println("翻炒中。。。。。。");
    }
    //出锅
    public void end(){
        System.out.println("出锅。。。。。。。");
    }
}
package com.example.design.template;

public class AutoCookMachine extends CookTemplate{
    @Override
    public void addfood() {
        System.out.println("加三个小白菜。。。。。。");
    }

    @Override
    public void addsalt() {
        System.out.println("放三勺盐。。。。。。。");
    }
}
package com.example.design.template;

public class MainTest {
    public static void main(String[] args) {
        AutoCookMachine autoCookMachine = new AutoCookMachine();
        autoCookMachine.cook();
    }
}
输出:
开火。。。。。。。。
加三个小白菜。。。。。。
放三勺盐。。。。。。。
翻炒中。。。。。。
出锅。。。。。。。
Disconnected from the target VM, address: '127.0.0.1:50875', transport: 'socket'
Process finished with exit code 0

策略模式

策略模式定义了一系列算法,并将每个算法封装起来,使他们可以相互替换,且算法的变化不会影响使用算法的客户,属于对象行为模式

策略模式的主要角色如下

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

未命名文件 84.png
例子

1、从北京到上海,有很多种策略到达,火车、飞机、高铁等等,每一种策略都可以达到相同的效果或目的。选择策略的依据是费用,时间,使用工具还有每种方式的方便程度。
2、打一局和平精英最终胜利路,策略有很多种,例如:稳健运营策略、冲锋向前策略。结果都是胜利。以此为实例如下
package com.example.design.strategy;

/**
 * 环境类
 */

public class TeamGNR {
    //抽取游戏策略算法,并进行引用
    private GameStrategy gameStrategy;

    public void setGameStrategy(GameStrategy gameStrategy) {
        this.gameStrategy = gameStrategy;
    }

    public void startGame(){
        System.out.println("游戏开始......");
        //游戏策略
        gameStrategy.warStrategy();
        System.out.println("win......");
    }
}
package com.example.design.strategy;

/**
 * 游戏策略
 */
public interface GameStrategy {
    //战斗策略
    void warStrategy();
}
package com.example.design.strategy;

/**
 * 稳健运营策略
 */
public class SteadyStrategy implements GameStrategy{

    @Override
    public void warStrategy() {
        System.out.println("各路小心。。。。及时支援。。。");
    }
}
package com.example.design.strategy;

/**
 * 冲锋向前策略
 */
public class UziStrategy implements GameStrategy{
    @Override
    public void warStrategy() {
        System.out.println("所有人向前冲");
    }
}
package com.example.design.strategy;

public class MainTest {
    public static void main(String[] args) {
        TeamGNR teamGNR = new TeamGNR();
        teamGNR.setGameStrategy(new UziStrategy());
        teamGNR.startGame();
        System.out.println("==================a");
        teamGNR.setGameStrategy(new SteadyStrategy());
        teamGNR.startGame();
    }
}
游戏开始......
所有人向前冲
win......
==================
游戏开始......
各路小心。。。。及时支援。。。
win......
Disconnected from the target VM, address: '127.0.0.1:51147', transport: 'socket'

状态模式

状态模式:对有状态的对象,把复杂的判断逻辑提取到不同的状态对象中,允许状态对象在其内部状态发生改变时改变其行为。

状态模式包含以下主要角色

环境类角色:也称为上下文,它定义了客户端需要的接口,内部维护一个当前状态,并负责具体状态的切换
抽象状态角色:定义一个接口,用以封装环境对象中的特定状态所对应的行为,可以有一个或多个行为
具体状态角色:实现抽象状态所对应的行为,并且在需要的情况下进行状态切换

未命名文件 83.png

package com.example.design.state;
/**
 * 抽象状态
 */
public interface TeamState {
    //玩游戏
    void playGame();

    //切换到下一个状态
    //状态的流转是状态模式的核心
    TeamState next();
}
package com.example.design.state;

/**
 * 吃牛肉面状态
 */
public class BeafNodleState implements TeamState{
    @Override
    public void playGame() {
        System.out.println("牛肉面真好吃。。。。。。");
    }

    @Override
    public TeamState next() {
        return new MatchState();
    }
}
package com.example.design.state;

/**
 * 竞赛状态
 */
public class MatchState implements TeamState{
    @Override
    public void playGame() {
        System.out.println("全力以赴打比赛。。。。。。");
    }

    @Override
    public TeamState next() {
        return new VocationState();
    }
}
package com.example.design.state;

/**
 * 休假状态
 */
public class VocationState implements TeamState{
    @Override
    public void playGame() {
        System.out.println("三亚旅游真舒服。。。饿了。。。不玩游戏");
        //状态流转

    }

    @Override
    public TeamState next() {
        return new BeafNodleState();
    }
}
package com.example.design.state;

/**
 * 环境类
 */
public class SKTTeam {

    private TeamState teamState;

    public void setTeamState(TeamState teamState) {
        this.teamState = teamState;
    }
    //开始游戏
    public void startGame(){
    //  状态不同会导致不同的游戏结果
        teamState.playGame();
    }
    //状态的流转
    void nextState(){
        teamState=teamState.next();
    }
}
package com.example.design.state;

public class MainTest {

    public static void main(String[] args) {
        SKTTeam sktTeam = new SKTTeam();
        VocationState vocationState = new VocationState();
        sktTeam.setTeamState(vocationState);
        sktTeam.startGame();
        sktTeam.nextState();
        sktTeam.startGame();
        sktTeam.nextState();
        sktTeam.startGame();
        System.out.println("===============");
    }
}
举报

相关推荐

0 条评论