14. Template Method模式代码

原创 2012年03月30日 21:44:17

    14. Template Method 本质:固定算法骨架
      14.1 实现应用系统的前台和后台的登录控制
        public class LoginModel {
            private String loginId;
            private String password;
            public String getLoginId() {
                return loginId;
            }
            public void setLoginId(String loginId) {
                this.loginId = loginId;
            }
            public String getPassword() {
                return password;
            }
            public void setPassword(String password) {
                this.password = password;
            }
        }
        public abstract class LoginTemplate {
            public final boolean login(LoginModel lm) {
                LoginModel lmFromDb = this.findLoginUser(lm.getLoginId());
                if (lmFromDb != null) {
                    String encryptPwd = this.encryptPwd(lm.getPassword());
                    lm.setPassword(encryptPwd);
                    return this.match(lm, lmFromDb);
                }
                return false;
            }
            public boolean match(LoginModel lm, LoginModel lmFromDb) {
                if (lm.getLoginId().equals(lmFromDb.getLoginId()) && lm.getPassword().equals(lmFromDb.getPassword())) {
                    return true;
                }
                return false;
            }
            public String encryptPwd(String password) {
                return password;
            }
            public abstract LoginModel findLoginUser(String loginId);
        }
        public class NormalLogin extends LoginTemplate{
            @Override
            public LoginModel findLoginUser(String loginId) {
                LoginModel lm = new LoginModel();
                lm.setLoginId(loginId);
                lm.setPassword("normal");
                return lm;
            }
        }
        public class WorkerLogin extends LoginTemplate{
            @Override
            public LoginModel findLoginUser(String loginId) {
                LoginModel lm = new LoginModel();
                lm.setLoginId(loginId);
                lm.setPassword("worker");
                return lm;
            }
            public String encryptPwd(String pwd) {
                System.out.println("Encrypt using MD5");
                return pwd;
            }
        }
        public class TemplateClient {
            public static void main(String[] args) {
                LoginModel lm = new LoginModel();
                lm.setLoginId("admin");
                lm.setPassword("worker");
                LoginTemplate lt = new WorkerLogin();
                LoginTemplate lt2 = new NormalLogin();
                System.out.println("Login portal: " + lt2.login(lm));
                System.out.println("Login console: " + lt.login(lm));
            }
        }
        /**
         * 封装进行登录控制所需要的数据,在公共数据的基础上,
         * 添加具体模块需要的数据
         */
        public class NormalLoginModel extends LoginModel{
            /**
             * 密码验证问题
             */
            private String question;
            /**
             * 密码验证答案
             */
            private String answer;
            public String getQuestion() {
                return question;
            }
            public void setQuestion(String question) {
                this.question = question;
            }
            public String getAnswer() {
                return answer;
            }
            public void setAnswer(String answer) {
                this.answer = answer;
            }
        }
        /**
         * 普通用户登录控制加强版的逻辑处理
         */
        public class NormalLogin2 extends LoginTemplate{
            @Override
            public LoginModel findLoginUser(String loginId) {
                NormalLoginModel nlm = new NormalLoginModel();
                nlm.setLoginId(loginId);
                nlm.setPassword("normal");
                nlm.setQuestion("question");
                nlm.setAnswer("answer");
                return nlm;
            }
            public boolean match(LoginModel lm, LoginModel lmFromDb) {
                //这个方法需要覆盖,因为现在进行登录控制的时候,
                //需要检测4个值是否正确,而不仅仅是缺省的2个
                //先调用父类实现好的,检测编号和密码是否正确
                boolean isSuperMatch = super.match(lm, lmFromDb);
                if (isSuperMatch) {
                    //如果编号和密码正确,继续检查问题和答案是否正确
                    //先把数据转换成自己需要的数据
                    NormalLoginModel nlm = (NormalLoginModel)lm;
                    NormalLoginModel nlmFromDb = (NormalLoginModel)lmFromDb;
                    //检查问题和答案是否正确
                    if (nlm.getQuestion().equals(nlmFromDb.getQuestion()) && nlm.getAnswer().equals(nlmFromDb.getAnswer())) {
                        return true;
                    }
                }
                return false;
            }
        }
        public class TemplateClient2 {
            public static void main(String[] args) {
                NormalLoginModel nlm = new NormalLoginModel();
                nlm.setLoginId("user");
                nlm.setPassword("normal");
                nlm.setQuestion("question");
                nlm.setAnswer("answer");
                LoginTemplate lt3 = new NormalLogin2();
                System.out.println("Login portal 2: " + lt3.login(nlm));
            }
        }
      14.2 重构时把相同的代码抽取到父类中, 然后通过钩子函数约束其行为。
        public abstract class HummerModel {
            /*
              * 首先,这个模型要能够被发动起来,别管是手摇发动,还是电力发动,反正
              * 是要能够发动起来,那这个实现要在实现类里了
              */
            protected abstract void start();
            //能发动,那还要能停下来,那才是真本事
            protected abstract void stop();
            //喇叭会出声音,是滴滴叫,还是哔哔叫
            protected abstract void alarm();
            //引擎会轰隆隆的响,不响那是假的
            protected abstract void engineBoom();
            //那模型应该会跑吧,别管是人退的,还是电力驱动,总之要会跑
            final public void run() {
                //先发动汽车
                this.start();
                //引擎开始轰鸣
                this.engineBoom();
                //通过钩子方法约束行为:要让它叫的就是就叫,喇嘛不想让它响就不响
                if(this.isAlarm()){
                    this.alarm();
                }
                //到达目的地就停车
                this.stop();
            }
            //钩子方法,默认喇叭是会响的
            protected  boolean isAlarm(){
                return true;
            }
        }
        public class HummerH1Model extends HummerModel {
            private boolean alarmFlag = true;  //是否要响喇叭
            @Override
            protected void alarm() {
                System.out.println("悍马H1鸣笛...");
            }
            @Override
            protected void engineBoom() {
                System.out.println("悍马H1引擎声音是这样在...");
            }
            @Override
            protected void start() {
                System.out.println("悍马H1发动...");
            }
            @Override
            protected void stop() {
                System.out.println("悍马H1停车...");
            }
            protected boolean isAlarm() {
                return this.alarmFlag;
            }
            //要不要响喇叭,是有客户的来决定的
            public void setAlarm(boolean isAlarm){
                this.alarmFlag = isAlarm;
            }
        }
        public class HummerH2Model extends HummerModel {
            protected void alarm() {
                System.out.println("悍马H2鸣笛...");
            }
            protected void engineBoom() {
                System.out.println("悍马H2引擎声音是这样在...");
            }
            protected void start() {
                System.out.println("悍马H2发动...");
            }
            protected void stop() {
                System.out.println("悍马H2停车...");
            }
            //默认没有喇叭的
            protected boolean isAlarm() {
                return false;
            }
        }
        public class Client {
            public static void main(String[] args) throws IOException {
                System.out.println("-------H1型号悍马--------");
                System.out.println("H1型号的悍马是否需要喇叭声响?0-不需要   1-需要");
                String type=(new BufferedReader(new InputStreamReader(System.in))).readLine();
                HummerH1Model h1 = new HummerH1Model();
                if(type.equals("0")){
                    h1.setAlarm(false);
                }
                h1.run();
                System.out.println("\n-------H2型号悍马--------");
                HummerH2Model h2 = new HummerH2Model();
                h2.run();
            }
        }

14、模板方法模式(Template Method)

14、模板方法模式(Template Method) 解释一下模板方法模式,就是指:一个抽象类中,有一个主方法,再定义1...n个方法,可以是抽象的,也可以是实际的方法,定义一个类,继承该抽象类,重写...
  • mixiu888
  • mixiu888
  • 2017年12月12日 08:26
  • 12597

14、模板方法模式(Template Method)

解释一下模板方法模式,就是指:一个抽象类中,有一个主方法,再定义1…n个方法,可以是抽象的,也可以是实际的方法,定义一个类,继承该抽象类,重写抽象方法,通过调用抽象类,实现对子类的调用....

JAVA设计模式(14) —<行为型>模板方法模式(Template Method)

1 定义: 模板方法模式(Template Method) Define the skeleton of an algorithm in anoperation, deferring some st...

设计模式与实例代码:Template Method模式

意图/定义:定义一个操作算法的骨架,将一些步骤推迟到子类中实现。使得子类可以不改变算法的结构而重定义此算法的步骤 问题:要完成在某一细节层次一致的一个过程或一系列步骤,全其个别步骤在更详细的层次上实...
  • zzulp
  • zzulp
  • 2012年04月11日 00:01
  • 538

Java设计模式—模板方法(Template Method)

模板是指在薄片塑料板上面写字后挖空,再使用毛笔或色笔涂满挖空部分,就能看到纯手工而以不失工整的字样,看到模板上的挖空形状,马上就知道最后会变出什么样子的字,不过实际上所显现出来的字样还是要依所使用的画...

在objective-c中实现模板方法模式(template method)

在ios中实现模板方法(template method)模式
  • kyfxbl
  • kyfxbl
  • 2013年12月02日 12:49
  • 3310

Template Method模板方法设计模式(类行为型)

概述在面向对象开发过程中,通常我们会遇到这样的一个问题:我们知道一个算法所需的关键步骤,并确定了这些步骤的执行顺序。但是某些步骤的具体实现是未知的,或者说某些步骤的实现与具体的环境相关。 例子1:银...

模板方法模式(Template Method Pattern)。

博文中的内容来源《设计模式之禅》这一本书,感激不尽。

模板方法模式【Template Method Pattern】

模板方法模式【Template Method Pattern】 周三,9:00,我刚刚坐到位置,打开电脑准备开始干活。 “小三,小三,叫一下其它同事,到会议室,开会”老大跑过来吼,带着淫笑。还不等...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:14. Template Method模式代码
举报原因:
原因补充:

(最多只允许输入30个字)