0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

お題は不問!Qiita Engineer Festa 2023で記事投稿!

oxゲーム (TicTacToe)を作ったので学んだことをシェア

Last updated at Posted at 2023-07-08

tl;dr

  • pythonをつかってconsoleで動くoxゲームを作りました。ソフトウェア・アーキテクチャ構築練習のために、スケーラビリティコードの読みやすさ使いやすさ を考慮して作成しています。
  • CPU vs CPU, CPU vs Player, Player vs Playerの3モードを制作しています。ゆくゆくはネットワークでの対戦機能も追加したり、Console以外でのinput / outputも追加してみたいと思います。
  • ゲームとしては特に難しいロジックはないですが、コードを読みやすくすることや、モジュール同士の組み合わせなどに想定以上に時間がかかりました。ただ自分で満足いく形になった時はレゴブロックを完成させたような達成感を味わえました。

制作物

Publicにしているため、もしよければ、コードレビューいただけると大変嬉しいです。
https://github.com/ZawaPaP/TicTacToe

学んだこと

  • コード内にマジックナンバーは使わない

    • マジックナンバーは何を意味しているのかわからない。Enumなどを使うようにする
  • 関数はBehaviorを表す

    • 各関数をどのクラスに配置するべきかに悩まされた。一つ指標になりそうなのが、関数はbehaviorを表すということ。関数名を動詞にするというのと相まって、しっくり来た
    • クラス、インスタンス変数に直接アクセスするのではなく、関数を使ってアクセスする。以下は例だがクラスの定数を取得するだけの関数を作成して、外部モジュールからは関数を使用して、アクセスする。
from game_mark import GameMark
from typing import Tuple

class BoardCell:
    def __init__(self) -> None:
        self.mark = GameMark.EMPTY.value

class GameBoard:
    ROW = 3
    COLUMN = 3

    def __init__(self) -> None:
        self.board = [[BoardCell() for _ in range(self.column())] for _ in range(self.row())]

    @staticmethod
    def row() -> int:
        return GameBoard.ROW

    @staticmethod
    def column() -> int:
        return GameBoard.COLUMN

  • 再帰について

    • 再帰はコードを追いづらく、エラーハンドリングもしづらいため可能な限り使わない。
    • ツリーやグラフなど親でも子でも帰ってくるデータが同じように見えるケースの場合のみ、使用を検討する
  • 命名

    • Handlerという名前をつけるなら、Handler内で処理を完結させ、Returnしないのが基本
  • Enum

    • Enumとは Enum(列挙型)は、プログラミングにおいて特定の値の集合を表現するためのデータ型です。Enumは、あるデータが特定の値の中から選ばれることを保証するために使用する。
  • IOとIO Controllerを分ける意味は?

    • IOはデータの入出力や外部リソースの操作に関する責任を持ち、IOコントローラモジュールはデータの制御やビジネスロジックに関する責任を持つ。これにより、コードの再利用性やテスト容易性が向上し、各モジュールの責務が明確になる。
  • @staticmethod

    • 静的メソッドは、クラスの中で共有のユーティリティ関数や、インスタンスに依存しない処理を実装する場合に便利。インスタンスの状態にアクセスする必要がない場合や、外部の依存関係を持たない単純な処理を実行する場合に使用。
  • try-exceptについて

    • 予期できるエラーは例外処理をすべき。予期できないエラーは異なる処理をしてexitすべき。例外処理は低い階層ではなく、controllerなどの層で制御を行う。そうすることにより例外発生した際の処理をまとめて書きやすくなる。
0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?