サザエさんで学ぶデザインパターン完全ガイド
![]() |
20万件以上の案件から、副業に最適なリモート・週3〜の案件を一括検索できるプラットフォーム。プロフィール登録でAIスカウトが自動的にマッチング案件を提案。市場統計や単価相場、エージェントの口コミも無料で閲覧可能なため、本業を続けながら効率的に高単価の副業案件を探せます。フリーランスボード |
| |
週2〜3日から働ける柔軟な案件が業界トップクラスの豊富さを誇るフリーランスエージェント。エンド直契約のため高単価で、週3日稼働でも十分な報酬を得られます。リモートや時間フレキシブルな案件も多数。スタートアップ・ベンチャー中心で、トレンド技術を使った魅力的な案件が揃っています。専属エージェントが案件紹介から契約交渉までサポート。利用企業2,000社以上の実績。ITプロパートナーズ |
| |
10,000件以上の案件を保有し、週3日〜・フルリモートなど柔軟な働き方に対応。高単価案件が豊富で、報酬保障制度(60%)や保険料負担(50%)など正社員並みの手厚い福利厚生が特徴。通勤交通費(月3万円)、スキルアップ費用(月1万円)の支給に加え、リロクラブ・freeeが無料利用可能。非公開案件80%以上、支払いサイト20日で安心して稼働できます。Midworks |
デザインパターンは難しそう…そう思っていませんか?この記事では、日本の国民的アニメ「サザエさん」の登場人物や日常シーンを使って、主要なデザインパターンを楽しく学べます。Pythonのサンプルコード付きで、実践的な理解も深められます。
この記事で学べること:
- デザインパターンの基本概念
- 5つの重要なデザインパターンの実装方法
- サザエさんの世界で理解する具体例
- 実務で使えるPythonコード
それでは、磯野家と一緒にデザインパターンの世界を探検しましょう!
目次
1. Singleton パターン:磯野家は世界に一つだけ
パターンの説明
Singletonパターンは、クラスのインスタンスが必ず1つだけになることを保証するパターンです。磯野家は世界に一つしか存在しないように、アプリケーション全体で一つのインスタンスのみを共有します。
サザエさんでの例
「磯野家」は桜新町に一軒しかありません。誰が訪ねても、同じ磯野家にたどり着きます。
Pythonサンプルコード
class IsonoHouse:
"""磯野家のSingletonクラス"""
_instance = None
def __new__(cls):
if cls._instance is None:
cls._instance = super().__new__(cls)
cls._instance.address = "東京都世田谷区桜新町"
cls._instance.family_members = ["サザエ", "マスオ", "タラオ", "波平", "フネ", "カツオ", "ワカメ"]
return cls._instance
def show_family(self):
print(f"磯野家の住所: {self.address}")
print(f"家族構成: {', '.join(self.family_members)}")
# 使用例
house1 = IsonoHouse()
house2 = IsonoHouse()
print(f"house1とhouse2は同じインスタンス: {house1 is house2}") # True
house1.show_family()
実務での活用シーン:
- データベース接続マネージャー
- アプリケーション設定管理
- ログ管理システム
2. Factory パターン:サザエさんの料理作り
パターンの説明
Factoryパターンは、オブジェクトの生成ロジックをカプセル化し、クライアントコードから分離するパターンです。具体的なクラスを指定せずにオブジェクトを生成できます。
サザエさんでの例
サザエさんは「今日は何を作ろうかしら」と考えながら、その日の気分や材料によって異なる料理を作ります。料理の種類は変わっても、「料理を作る」という行為は同じです。
Pythonサンプルコード
from abc import ABC, abstractmethod
# 抽象的な料理クラス
class Dish(ABC):
@abstractmethod
def prepare(self):
pass
@abstractmethod
def cook(self):
pass
# 具体的な料理クラス
class Curry(Dish):
def prepare(self):
return "野菜とお肉を切ります"
def cook(self):
return "カレールーで煮込みました!美味しいカレーの完成!"
class Miso_Soup(Dish):
def prepare(self):
return "豆腐とワカメを準備します"
def cook(self):
return "お味噌を溶いて完成!あったかいお味噌汁ができました"
class Hamburg(Dish):
def prepare(self):
return "ひき肉をこねてハンバーグの形にします"
def cook(self):
return "フライパンで焼きました!ジューシーなハンバーグの出来上がり"
# サザエさんの料理工場
class SazaeCookingFactory:
@staticmethod
def create_dish(dish_type: str) -> Dish:
dishes = {
"カレー": Curry,
"味噌汁": Miso_Soup,
"ハンバーグ": Hamburg
}
dish_class = dishes.get(dish_type)
if dish_class:
return dish_class()
else:
raise ValueError(f"{dish_type}は作れません...")
# 使用例
print("【今日の夕食作り】")
dinner = SazaeCookingFactory.create_dish("カレー")
print(f"1. {dinner.prepare()}")
print(f"2. {dinner.cook()}")
print()
print("【お味噌汁も作ります】")
soup = SazaeCookingFactory.create_dish("味噌汁")
print(f"1. {soup.prepare()}")
print(f"2. {soup.cook()}")
実務での活用シーン:
- UI コンポーネントの生成
- データベースコネクションの作成
- ドキュメント生成システム
3. Observer パターン:家族みんなが気にする波平さんの帰宅
パターンの説明
Observerパターンは、あるオブジェクトの状態変化を、それに依存する複数のオブジェクトに自動的に通知するパターンです。
サザエさんでの例
波平さんが「ただいま〜!」と帰宅すると、家族全員がそれに反応します。サザエさんは「お父さん、お帰りなさい!」、カツオは「おじいちゃん帰ってきた!」と、それぞれが独自の反応をします。
Pythonサンプルコード
from typing import List, Protocol
# Observer インターフェース
class FamilyMember(Protocol):
def update(self, message: str):
pass
# 具体的なオブザーバー
class Sazae:
def update(self, message: str):
print(f"サザエ: 「お父さん、{message}!夕飯できてますよ」")
class Katsuo:
def update(self, message: str):
print(f"カツオ: 「おじいちゃん{message}!今日の野球見た?」")
class Wakame:
def update(self, message: str):
print(f"ワカメ: 「お父さん{message}♪ お疲れ様です」")
class Fune:
def update(self, message: str):
print(f"フネ: 「あなた、{message}。お茶をいれますね」")
# Subject(被観察者)
class Namihei:
def __init__(self):
self._observers: List[FamilyMember] = []
def attach(self, observer: FamilyMember):
"""家族メンバーを登録"""
self._observers.append(observer)
print(f"{observer.__class__.__name__}が波平さんの帰宅を待っています")
def detach(self, observer: FamilyMember):
"""家族メンバーの登録を解除"""
self._observers.remove(observer)
def arrive_home(self):
"""帰宅時に全員に通知"""
print("\n【波平さんが帰宅しました】")
print("波平: 「ただいま〜!」\n")
self._notify("お帰りなさい")
def _notify(self, message: str):
"""全オブザーバーに通知"""
for observer in self._observers:
observer.update(message)
# 使用例
namihei = Namihei()
# 家族メンバーを登録
sazae = Sazae()
katsuo = Katsuo()
wakame = Wakame()
fune = Fune()
namihei.attach(sazae)
namihei.attach(katsuo)
namihei.attach(wakame)
namihei.attach(fune)
print()
# 波平さんが帰宅
namihei.arrive_home()
実務での活用シーン:
- イベント駆動システム
- UI更新の自動化
- リアルタイム通知システム
4. Strategy パターン:カツオの宿題戦略
パターンの説明
Strategyパターンは、アルゴリズムをカプセル化し、実行時に切り替えられるようにするパターンです。同じ目的を達成するための複数の方法を柔軟に選択できます。
サザエさんでの例
カツオが宿題に取り組む方法は状況によって変わります。締め切りまで時間があれば真面目にコツコツ、締め切り間際なら中島くんに教えてもらう、どうしようもなければワカメに泣きつく…など、状況に応じて戦略を変えます。
Pythonサンプルコード
from abc import ABC, abstractmethod
from datetime import datetime, timedelta
# 戦略のインターフェース
class HomeworkStrategy(ABC):
@abstractmethod
def do_homework(self, subject: str) -> str:
pass
# 具体的な戦略1: 自分でやる
class SelfStudyStrategy(HomeworkStrategy):
def do_homework(self, subject: str) -> str:
return f"よし!{subject}の宿題を自分でやるぞ!時間をかけて丁寧にやろう"
# 具体的な戦略2: 中島くんに聞く
class AskNakajimaStrategy(HomeworkStrategy):
def do_homework(self, subject: str) -> str:
return f"中島〜!{subject}の宿題教えてくれよ〜。一緒にやろうぜ!"
# 具体的な戦略3: ワカメに泣きつく
class AskWakameStrategy(HomeworkStrategy):
def do_homework(self, subject: str) -> str:
return f"ワカメ〜、お兄ちゃん{subject}の宿題分かんないんだ...ヒントちょうだいよ〜(涙)"
# 具体的な戦略4: 諦める
class GiveUpStrategy(HomeworkStrategy):
def do_homework(self, subject: str) -> str:
return f"{subject}の宿題?明日先生に怒られるけど...まあいいや!遊びに行こう!"
# カツオクラス
class Katsuo:
def __init__(self):
self.strategy: HomeworkStrategy = None
def set_strategy(self, strategy: HomeworkStrategy):
"""宿題戦略を設定"""
self.strategy = strategy
def execute_homework(self, subject: str, deadline: datetime):
"""宿題を実行"""
now = datetime.now()
time_left = deadline - now
print(f"\n【{subject}の宿題】")
print(f"締め切りまで: {time_left.days}日")
# 状況に応じて戦略を自動選択
if time_left.days >= 3:
self.set_strategy(SelfStudyStrategy())
print("カツオ: 「まだ時間あるな!」")
elif time_left.days >= 1:
self.set_strategy(AskNakajimaStrategy())
print("カツオ: 「ちょっとヤバいかも...」")
elif time_left.days == 0 and time_left.seconds > 3600:
self.set_strategy(AskWakameStrategy())
print("カツオ: 「やばい!今日中だ!」")
else:
self.set_strategy(GiveUpStrategy())
print("カツオ: 「もう手遅れだ...」")
result = self.strategy.do_homework(subject)
print(f"カツオ: 「{result}」")
# 使用例
katsuo = Katsuo()
# シナリオ1: 締め切りまで5日
deadline1 = datetime.now() + timedelta(days=5)
katsuo.execute_homework("算数", deadline1)
# シナリオ2: 締め切りまで2日
deadline2 = datetime.now() + timedelta(days=2)
katsuo.execute_homework("国語", deadline2)
# シナリオ3: 締め切り当日
deadline3 = datetime.now() + timedelta(hours=5)
katsuo.execute_homework("理科", deadline3)
実務での活用シーン:
- 支払い方法の選択(クレカ、銀行振込、電子マネー)
- データ圧縮アルゴリズムの切り替え
- 検索アルゴリズムの最適化
5. Decorator パターン:タラオちゃんの着替え
パターンの説明
Decoratorパターンは、既存のオブジェクトに動的に新しい機能を追加するパターンです。継承を使わずに、オブジェクトを装飾(デコレート)することで機能を拡張できます。
サザエさんでの例
タラオちゃんが外出する時、基本の服装に、帽子をかぶったり、マフラーを巻いたり、コートを着たりと、どんどん装飾を追加していきます。
Pythonサンプルコード
from abc import ABC, abstractmethod
# 基本コンポーネント
class Character(ABC):
@abstractmethod
def description(self) -> str:
pass
@abstractmethod
def warmth_level(self) -> int:
pass
# 具体的なコンポーネント
class Tarao(Character):
def description(self) -> str:
return "タラオちゃん(半袖シャツとズボン)"
def warmth_level(self) -> int:
return 10 # 基本の暖かさ
# デコレーターの基底クラス
class ClothingDecorator(Character):
def __init__(self, character: Character):
self._character = character
@abstractmethod
def description(self) -> str:
pass
@abstractmethod
def warmth_level(self) -> int:
pass
# 具体的なデコレーター1: 帽子
class Hat(ClothingDecorator):
def description(self) -> str:
return f"{self._character.description()} + 黄色い帽子"
def warmth_level(self) -> int:
return self._character.warmth_level() + 5
# 具体的なデコレーター2: コート
class Coat(ClothingDecorator):
def description(self) -> str:
return f"{self._character.description()} + 冬用コート"
def warmth_level(self) -> int:
return self._character.warmth_level() + 20
# 具体的なデコレーター3: マフラー
class Scarf(ClothingDecorator):
def description(self) -> str:
return f"{self._character.description()} + ふわふわマフラー"
def warmth_level(self) -> int:
return self._character.warmth_level() + 10
# 具体的なデコレーター4: 手袋
class Gloves(ClothingDecorator):
def description(self) -> str:
return f"{self._character.description()} + 手袋"
def warmth_level(self) -> int:
return self._character.warmth_level() + 8
# 使用例
print("【タラオちゃんの着替えタイム】\n")
# 基本のタラオちゃん
tarao = Tarao()
print(f"1. {tarao.description()}")
print(f" 暖かさレベル: {tarao.warmth_level()}\n")
# 帽子を追加
tarao_with_hat = Hat(tarao)
print(f"2. {tarao_with_hat.description()}")
print(f" 暖かさレベル: {tarao_with_hat.warmth_level()}\n")
# さらにマフラーを追加
tarao_with_scarf = Scarf(tarao_with_hat)
print(f"3. {tarao_with_scarf.description()}")
print(f" 暖かさレベル: {tarao_with_scarf.warmth_level()}\n")
# 完全装備(コートと手袋も)
tarao_full = Gloves(Coat(tarao_with_scarf))
print(f"4. {tarao_full.description()}")
print(f" 暖かさレベル: {tarao_full.warmth_level()}")
print(" サザエさん: 「これで公園に行っても大丈夫ですぅ!」")
実務での活用シーン:
- ロギング機能の追加
- キャッシュ機能の追加
- 権限チェックの追加
デザインパターンを学ぶメリット
1. コードの再利用性向上
よくある問題に対する実証済みの解決策を使用できます。
2. チーム開発での共通言語
「このコードはSingletonで実装しよう」と言えば、チーム全員が同じイメージを持てます。
3. 保守性の向上
パターンに従ったコードは、他の開発者にとっても理解しやすくなります。
4. 設計スキルの向上
様々なパターンを学ぶことで、より良いソフトウェア設計ができるようになります。
まとめ:デザインパターンは難しくない!
この記事では、サザエさんの日常を通じて5つの重要なデザインパターンを学びました:
- Singleton: 磯野家は一つだけ
- Factory: サザエさんの料理作り
- Observer: 家族が波平さんの帰宅を待つ
- Strategy: カツオの宿題戦略
- Decorator: タラオちゃんの着替え
デザインパターンは決して難しいものではありません。日常生活の中にある考え方を、プログラミングに応用したものです。
次のステップ
- 他のデザインパターン(Adapter、Template Method、Commandなど)も学んでみましょう
- 実際のプロジェクトで適切なパターンを選択する練習をしましょう
- 「Gang of Four(GoF)のデザインパターン」の書籍を読んでみましょう
サザエさんと一緒に学んだデザインパターン、ぜひ実務で活用してください!
関連キーワード
デザインパターン Python, GoF デザインパターン, オブジェクト指向, ソフトウェア設計, プログラミング初心者, Pythonサンプルコード, Singleton パターン, Factory パターン, Observer パターン, Strategy パターン, Decorator パターン
最終更新日: 2025年11月
![]() |
20万件以上の案件から、副業に最適なリモート・週3〜の案件を一括検索できるプラットフォーム。プロフィール登録でAIスカウトが自動的にマッチング案件を提案。市場統計や単価相場、エージェントの口コミも無料で閲覧可能なため、本業を続けながら効率的に高単価の副業案件を探せます。フリーランスボード |
| |
週2〜3日から働ける柔軟な案件が業界トップクラスの豊富さを誇るフリーランスエージェント。エンド直契約のため高単価で、週3日稼働でも十分な報酬を得られます。リモートや時間フレキシブルな案件も多数。スタートアップ・ベンチャー中心で、トレンド技術を使った魅力的な案件が揃っています。専属エージェントが案件紹介から契約交渉までサポート。利用企業2,000社以上の実績。ITプロパートナーズ |
| |
10,000件以上の案件を保有し、週3日〜・フルリモートなど柔軟な働き方に対応。高単価案件が豊富で、報酬保障制度(60%)や保険料負担(50%)など正社員並みの手厚い福利厚生が特徴。通勤交通費(月3万円)、スキルアップ費用(月1万円)の支給に加え、リロクラブ・freeeが無料利用可能。非公開案件80%以上、支払いサイト20日で安心して稼働できます。Midworks |








