You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

策略模式如何改变应用运行时行为而模板模式却不能?为何二者可运行时选择却有动静行为之分?

Great questions—these are exactly the kind of nuanced pattern distinctions that trip up even experienced devs if you don’t dig into how they’re implemented. Let’s break them down one by one.

1. How Strategy Pattern Changes Runtime Behavior (When Template Method Can’t)

The core difference boils down to composition vs. inheritance, and how each pattern locks in behavior:

  • Strategy uses composition: Every variant of behavior is wrapped in its own standalone "strategy" class that implements a common interface. The main "context" class holds a reference to a strategy object—and here’s the key: you can swap that reference out at any point while the program is running.
    For example, think of a music player: you could switch between a "NormalPlaybackStrategy" and a "ShufflePlaybackStrategy" mid-playlist, without restarting the player or creating a new instance. The behavior changes dynamically, during runtime.

  • Template Method uses inheritance: The parent class defines a fixed "skeleton" of an algorithm (like "boil water → add ingredient → pour into cup"), and subclasses override specific steps. Once you instantiate a subclass (say, CoffeeMaker instead of TeaMaker), that object’s behavior is baked in. You can’t reconfigure it to act like the other subclass without discarding the original object and creating a new one. The algorithm’s steps are fixed at instantiation, not dynamic during runtime.

2. If We Can "Choose" Both at Runtime, Why Call Strategy "Runtime" and Template "Static"?

The confusion here comes from mixing up "choosing a variant" with "modifying behavior after instantiation":

  • Strategy lets you modify behavior during an object’s lifetime: Choosing a strategy isn’t just about picking one at startup. You can update the context’s strategy reference while the program is actively running. For example, a game character could switch from a "DefensiveStrategy" to an "OffensiveStrategy" mid-battle, without creating a new character object. The behavior changes in-place, on the fly.

  • Template Method’s behavior is static after instantiation: "Choosing" a Template Method variant means creating an instance of a specific subclass. Once that object exists, its behavior can’t change—you can’t rewire a CoffeeMaker to suddenly add tea leaves instead of coffee grounds. The "choice" happens at object creation (which can be at runtime), but the object’s behavior is fixed for its entire lifetime. It’s "static" in the sense that the object’s algorithm doesn’t evolve after it’s created.

Quick Code Examples to Drive This Home

Strategy Pattern (Runtime Switching)

class PaymentStrategy:
    def pay(self, amount):
        pass

class AlipayStrategy(PaymentStrategy):
    def pay(self, amount):
        print(f"Paid ${amount} via Alipay")

class WeChatPayStrategy(PaymentStrategy):
    def pay(self, amount):
        print(f"Paid ${amount} via WeChat Pay")

class PaymentProcessor:
    def __init__(self, strategy):
        self.strategy = strategy
    
    def switch_strategy(self, new_strategy):
        self.strategy = new_strategy  # Runtime swap
    
    def process_payment(self, amount):
        self.strategy.pay(amount)

# Usage
processor = PaymentProcessor(AlipayStrategy())
processor.process_payment(100)  # Paid $100 via Alipay
processor.switch_strategy(WeChatPayStrategy())
processor.process_payment(50)   # Paid $50 via WeChat Pay (switched mid-session)

Template Method (Static Behavior Post-Instantiation)

class BeverageMaker:
    def make_beverage(self):
        self.boil_water()
        self.add_ingredient()
        self.pour_in_cup()
    
    def boil_water(self):
        print("Boiling water...")
    
    def pour_in_cup(self):
        print("Pouring into cup...")
    
    # To be overridden by subclasses
    def add_ingredient(self):
        pass

class CoffeeMaker(BeverageMaker):
    def add_ingredient(self):
        print("Adding coffee grounds")

class TeaMaker(BeverageMaker):
    def add_ingredient(self):
        print("Adding tea leaves")

# Usage
coffee_maker = CoffeeMaker()
coffee_maker.make_beverage()  # Makes coffee—can't make tea without a new instance
# No way to make coffee_maker add tea leaves after it's created!

内容的提问来源于stack exchange,提问作者soodankit

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.08 14:22:40