導入
Commandは「操作をオブジェクトとして表現」——実行・取り消し・キュー化ができるように。Chain of Responsibilityは「処理役を数珠つなぎにし、扱える者が処理」——承認フローやミドルウェアの構造です。
図解
flowchart LR
R["要求"] --> H1["担当A<br/>扱える?"]
H1 -->|無理| H2["担当B<br/>扱える?"]
H2 -->|無理| H3["担当C<br/>処理"]
サンプル
// Command: 操作をオブジェクト化して、あとでまとめて実行
var history = new List<ICommand>
{
new PrintCommand("A"),
new PrintCommand("B"),
};
foreach (var cmd in history) cmd.Execute(); // 実行: A / 実行: B
// Chain of Responsibility: 承認額に応じて担当者を数珠つなぎで探す
var chain = new Leader(new Manager(null));
chain.Approve(80000); // 課長が承認: 80000円
chain.Approve(300000); // 部長が承認: 300000円
interface ICommand { void Execute(); }
class PrintCommand : ICommand
{
private readonly string _label;
public PrintCommand(string label) => _label = label;
public void Execute() => Console.WriteLine($"実行: {_label}");
}
abstract class Approver
{
protected Approver? Next;
protected Approver(Approver? next) => Next = next;
public abstract void Approve(int amount);
}
class Leader : Approver
{
public Leader(Approver? next) : base(next) { }
public override void Approve(int amount)
{
if (amount <= 100000) Console.WriteLine($"課長が承認: {amount}円");
else Next?.Approve(amount); // 扱えなければ次へ回す
}
}
class Manager : Approver
{
public Manager(Approver? next) : base(next) { }
public override void Approve(int amount) => Console.WriteLine($"部長が承認: {amount}円");
}
- Command: 操作を
Execute()を持つオブジェクトにし、履歴・キュー・取り消しに対応できる - Chain of Responsibility: 処理役を連結し、「自分が扱えなければ次へ回す」
- どちらも「呼び出し側」と「処理内容」を切り離す
演習
ICommand cmd = new GreetCommand("Taro");
cmd.Execute(); // こんにちは、Taro
// TODO: Execute() で "こんにちは、名前" を出力する GreetCommand を定義してください
interface ICommand { void Execute(); }
___
- 期待される出力:
こんにちは、Taro
ヒント1を見る
名前をフィールドに持ち、Executeで出力します
ヒント2を見る
class GreetCommand : ICommand { private readonly string _name; public GreetCommand(string name) => _name = name; public void Execute() => Console.WriteLine($"こんにちは、{_name}"); }
まとめ
- Commandは操作をオブジェクト化し、実行・履歴・取り消しを可能にする
- Chain of Responsibilityは処理役を連結し順に委ねる
- どちらも呼び出しと処理内容を分離する
次回: 手順の骨組みと反復のTemplate Method/Iteratorです。