Java设计模式:模板模式

使用场景

在一些特定的情形中,整个事务流程中有着固定的某些步骤,例如豆浆的生产过程可简化为:①选取豆材 ②加入配料 ③研磨 ,又例如在去银行办业务,基本的流程为:①挂号排队 ②办理业务 ③服务评分 ,在这一类型的事物中,往往都是有着固定的运行流程,而在流程中不同的部分仅仅只是某一步,例如豆浆的②加入配料,这里可以加入不同的配料,加入什么配料由执行者决定,银行的业务也是同样的道理。基于这类情形,我们可以通过模板模式来设计我们的代码。

介绍

模板模式:

  • 一个抽象类定义了公有的模板/算法来执行其内部的方法,它的子类可以重新定义父类中的某一方法,但是执行步骤按照父类定义的模板/算法来实现。
  • 是一种行为型模式

下面给出一种例子,大概实现的功能是:
在银行ATM自助机执行存/储两种操作。

UML类图如下:
在这里插入图片描述
ATM操作的抽象类,定义了基本的四个执行过程:

  1. 插入进行卡
  2. 输出密码
  3. 执行所选业务
  4. 退出银行卡

同时有一个不可变的use()方法,作为其子类的执行模板,子类必须按照定义的模板来顺序执行相应的方法。
内有一个抽象方法abstract void service(),子类必须重写这个方法来具体实现。

public abstract class AbstractATM {
	//模板
    public final void use(){
        card();
        password();
        service();
        exit();
    }
    
    protected void card(){
        System.out.println("请放入银行卡");
    }
    protected void password(){
        System.out.println("请输入密码");
    }
    //由子类实现其具体功能
    protected abstract void service();

    protected void exit(){
        System.out.println("欢迎再次使用");
    }
}

子类重写service方法,为存储操作:

public class DepositATM extends AbstractATM {
    @Override
    protected void service() {
        System.out.println("执行存钱业务");
    }
}

子类重写service方法,为取钱操作:

public class WithdrawATM extends AbstractATM {
    @Override
    protected void service() {
        System.out.println("执行取钱业务");
    }
}

客户端新建一个存钱或取钱的对象,调用use()方法,实现使用ATM存储机的整个过程:

public class Client {
    public static void main(String[] args) {
        AbstractATM depositATM = new DepositATM();
        depositATM.use();

        AbstractATM withdrawATM = new WithdrawATM();
        withdrawATM.use();
    }
}

运行结果如下:

请放入银行卡
请输入密码
执行存钱业务
欢迎再次使用

请放入银行卡
请输入密码
执行取钱业务
欢迎再次使用

钩子方法

若我们在ATM前突然有急事需要马上离开或者不想继续操作了,或者以上面的豆浆为例子,我们并不想要添加配料。
此时,我们添加一个判断方法:

public abstract class AbstractATM {
    public final void use(){
        card();
        password();
        //如果反悔不为真,则执行服务
        if (!regret()) service();
        exit();
    }
    //添加一个返回的函数,子类可以按情况重写
    boolean regret(){
        return false;
    }

    protected void card(){
        System.out.println("请放入银行卡");
    }
    protected void password(){
        System.out.println("请输入密码");
    }
    //由子类实现其具体功能
    protected abstract void service();

    protected void exit(){
        System.out.println("欢迎再次使用");
    }
}

相应的子类重写方法(只在存钱类重写了regret方法):

public class DepositATM extends AbstractATM {
    @Override
    protected void service() {
        System.out.println("执行存钱业务");
    }

    @Override
    boolean regret() {
        return true;
    }
}

同样的客户端调用:

public class Client {
    public static void main(String[] args) {
        AbstractATM depositATM = new DepositATM();
        depositATM.use();

        AbstractATM withdrawATM = new WithdrawATM();
        withdrawATM.use();
    }
}

这时候同样的客户端输出为:

请放入银行卡
请输入密码
欢迎再次使用

请放入银行卡
请输入密码
执行取钱业务
欢迎再次使用

可以发现存钱类并没有执行它的service方法。

这种方法叫做钩子方法,可根据业务需求来重写钩子方法。

总结

优点:

  1. 封装不变部分,扩展变化部分;

  2. 便于维护;

  3. 执行顺序由父类控制,行为由子类实现。

缺点: 每个实现都需要由不同的子类实现,类数量过多。
关键: 父类定义执行步骤(一般由final修饰),子类实现具体行为。
应用: 有固定方法步骤,可执行不同行为的情形。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
面有两个帐号: 帐号:1 PIN:42 帐号:2 PIN:1234 原文是如下: To run the simulation above, you need to do the following: 1.Click on the "ON" button (lower right-hand corner) to turn the ATM on. 2.Enter the number of $20 bills you want to have be in the cash dispenser at the start of the simulation when you are prompted to do so, and press RETURN 3.Perform any number of sessions, as follows: 1.Click on the "Click to insert card" button to simulate inserting a card 2.Type in the card number when you are prompted to do so (see below), and press RETURN 3.Enter the PIN associated with the card (see below). Although you can use your regular keyboard, it's more fun to click on the keys on the simulated ATM keyboard as displayed. 4.Perform any number of transactions, using your mouse to click the keys on the simulated ATM keyboard. Note that the machine will simulate ejecting your card when you indicate you do not wish to perform any more transactions (unless, of course, your card is retained due to too many invalid PINs). 4.Turn off the ATM by clicking on the "OFF" button (same position as the "ON" button". Note that you cannot turn the ATM off while in the middle of a customer session. 5.The entire simulation may be repeated as many times as you want, by turning the machine ON again. For demonstration purposes, this program uses a very simple simulation of the bank, with hardwired card numbers and PIN's, etc. The following are the available cards: Card Number PIN Available accounts 1 42 Checking account #1, Savings account #2 2 1234 Checking account #1, Money market account #3 (Note that both cards link to the same checking account) All the features of the bank work - both current and available balances (initially the same) are maintained for each account and a $300 daily withdrawal limit per card is enforced.

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值