模版方法模式
模板方法模式
定义了一个算法的步骤,并允许子类别为一个或多个步骤提供其实践方式。让子类别在不改变算法架构的情况下,重新定义算法中的某些步骤。
一、常见使用的场景
如 Thread 类。我们知道在 Java 中一种 实现线程执行单元的方式 是定义一个类继承 Thread 类然后重写其中的 run 方法,此时 run 方法中的逻辑是由我们去自己写的,通过调用 start() 方法我们可以使得创建好的线程进入 可运行状态 然后 JVM 会去调用对应的 run 方法执行。
public synchronized void start() { /** * This method is not invoked for the main method thread or "system" * group threads created/set up by the VM. Any new functionality added * to this method in the future may have to also be added to the VM. * * A zero status value corresponds to state "NEW". */ if (threadStatus != 0) throw new IllegalThreadStateException(); /* Notify the group that this thread is about to be started * so that it can be added to the group's list of threads * and the group's unstarted count can be decremented. */ group.add(this); boolean started = false; try { start0(); started = true; } finally { try { if (!started) { group.threadStartFailed(this); } } catch (Throwable ignore) { /* do nothing. If start0 threw a Throwable then it will be passed up the call stack */ } } } private native void start0();
二、简单示例
上面常见场景会有些抽象,应为有些东西对我们是不可见的,所以这里通过一个简单例子理解。
首先我们定义一个父类
此类:定义了一个算法的步骤,类似于 Thread 定义类需要线程执行的代码 run 的被调用步骤(即:这个方法在一个执行流程中,这个流程虽然我们没有办法控制,但是流程中的具体步骤我们可以根据具体情况实现)
package templatemethod; /** * 模板方法类:可以看到这里我们只是给了一个做西红柿炒鸡蛋的步骤(一个算法步骤) */ public abstract class Cook { abstract void oil(); // 食用油 abstract void egg(); // 鸡蛋 abstract void tomato(); // 西红柿 // 封装具体的行为:做饭 public final void cook() { this.oil(); this.egg(); this.tomato(); } }
然后我们编写两个子类
这两个类就类似于你编写了两个不同的类继承 Thread 类并重写了 run 方法
package templatemethod; /** * 定义一个我的类 */ public class Me extends Cook{ @Override void oil() { System.out.println("自己:油放多了"); } @Override void egg() { System.out.println("自己:鸡蛋糊了"); } @Override void tomato() { System.out.println("自己:番茄没熟"); } }
package templatemethod; /** * 定义一个厨师类 */ public class Chef extends Cook{ @Override void oil() { System.out.println("厨师:油适量"); } @Override void egg() { System.out.println("厨师:鸡蛋煎至金黄"); } @Override void tomato() { System.out.println("厨师:番茄炒至入味"); } }
测试
package templatemethod; /** * 测试调用类 */ public class Main { public static void main(String[] args) { new Chef().cook(); new Me().cook(); } } // 输出: 厨师:油适量 厨师:鸡蛋煎至金黄 厨师:番茄炒至入味 自己:油放多了 自己:鸡蛋糊了 自己:番茄没熟
三、总结
适用于处理某一个流程的代码我们已经可以确定,但是其中某一个或以上的具体步骤我们暂时不能确定,因此通过模板方法模式,将这个步骤中的一步或者几步的具体实现转交给子类完成。即:处理步骤父类中定义好,具体实现延迟到子类中定义。
本文作者:编程初学者求大佬指点
本文链接:https://www.cnblogs.com/fragmentary/p/18380020
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步