Приведите пример использования паттерна Strategy в разных языках (например Python, Java, JavaScript) и обсудите преимущества композиции поведения над наследованием

10 Сен в 04:12
2 +2
0
Ответы
1
Коротко: паттерн Strategy инкапсулирует семейство алгоритмов в отдельные объекты (стратегии) и позволяет менять поведение контекста динамически через композицию, а не через наследование.
Пример (Python)
class CreditCardPayment:
def pay(self, amount):
print(f"Paying {amount} by credit card")
class PayPalPayment:
def pay(self, amount):
print(f"Paying {amount} via PayPal")
class Order:
def __init__(self, strategy):
self.strategy = strategy
def set_strategy(self, strategy):
self.strategy = strategy
def pay(self, amount):
self.strategy.pay(amount)
# Использование:
order = Order(CreditCardPayment())
amount = 100100100 order.pay(amount) # кредитная карта
order.set_strategy(PayPalPayment())
order.pay(amount) # PayPal
Пример (Java)
interface PaymentStrategy {
void pay(int amount);
}
class CreditCardPayment implements PaymentStrategy {
public void pay(int amount) { System.out.println("Paying " + amount + " by card"); }
}
class PayPalPayment implements PaymentStrategy {
public void pay(int amount) { System.out.println("Paying " + amount + " via PayPal"); }
}
class Order {
private PaymentStrategy strategy;
Order(PaymentStrategy strategy){ this.strategy = strategy; }
void setStrategy(PaymentStrategy s){ this.strategy = s; }
void pay(int amount){ strategy.pay(amount); }
}
// Использование:
Order order = new Order(new CreditCardPayment());
int amount = 100100100;
order.pay(amount);
order.setStrategy(new PayPalPayment());
order.pay(amount);
Пример (JavaScript)
const creditCardPayment = {
pay: amount => console.log(`Paying ${amount} by card`)
};
const payPalPayment = {
pay: amount => console.log(`Paying ${amount} via PayPal`)
};
class Order {
constructor(strategy){ this.strategy = strategy; }
setStrategy(s){ this.strategy = s; }
pay(amount){ this.strategy.pay(amount); }
}
const order = new Order(creditCardPayment);
const amount = 100100100;
order.pay(amount);
order.setStrategy(payPalPayment);
order.pay(amount);
Преимущества композиции поведения (Strategy) над наследованием
- Гибкость в рантайме: поведение можно менять динамически (setStrategy) без создания новых подклассов.
- Меньше классов/комбинаций: вместо взрывного роста подклассов для каждой комбинации поведения, композиция сводит число вариантов от m×nm \times nm×n к примерно m+nm + nm+n.
- Разделение обязанностей: алгоритмы в отдельной иерархии (Single Responsibility).
- Тестируемость: стратегии легко мокать и тестировать отдельно.
- Открытость/закрытость: новые стратегии добавляются без изменения контекста (OCP).
- Снижение связности и «хрупкости базового класса»: изменения в базовом классе не ломают все наследников.
- Повторное использование: одна стратегия может применяться в разных контекстах.
Короткий компромисс: композиция добавляет уровень делегирования/индикации (слегка больше кода и косвенности), но выигрыши в гибкости и сопровождении обычно перевешивают.
10 Сен в 04:19
Не можешь разобраться в этой теме?
Обратись за помощью к экспертам
Гарантированные бесплатные доработки в течение 1 года
Быстрое выполнение от 2 часов
Проверка работы на плагиат
Поможем написать учебную работу
Прямой эфир