simudaru's blog

Python, Rなどのメモを残していこうと思います。  よろしくお願いいたします。

Pythonでジャンケンゲーム作る(その1.1)

中途半端なのは承知で、自分用メモ。
途中経過を貼っておきます。

苦手なオブジェクト指向プログラミングに挑戦中です。
一応動く状態までは作りましたが、設計ちゃんとしないとですね。

もう少しきれいにしたら、複数人でのジャンケンもできるように変更予定です。

# -*- coding: utf-8 -*-
import time
import random

const_max_win = 3
const_num_player = 2  # うち一人はプレイヤー
hand_dict = {"r":1, "s":2, "p":3}
hand_print_dict = {1:"グー", 2:"チョキ", 3:"パー"}


class GameRPS:
    
    def __init__(self):
        self.win_count_goal = 3
    
    # ジャンケンゲームを開始する
    def start_game_rps(self, player_list):
        print "じゃんけんスタート。"
        time.sleep(1.0)
        
        flg_draw = False
        while not self.judge_max_win_count(player_list):
            
            # 正しいプレイヤーの手が入力されるまでループ
            while 1:
                # メッセージ
                if flg_draw:
                    print "あい"
                    time.sleep(0.5)
                    print "こで"
                    time.sleep(0.5)
                    print "……"
                else:
                    print "じゃん"
                    time.sleep(0.5)
                    print "けん"
                    time.sleep(0.5)
                    print "……"
                
                # プレイヤーの手
                phand = [0]*len(player_list)
                for i in range(len(player_list)):
                    player_list[i].decide_hand()
                    phand[i] = player_list[i].get_hand()
                
                # プレイヤーの手が正しければループを抜ける
                if set(phand).issubset(set([1,2,3])):
                    break
            
            # メッセージ
            if flg_draw:
                print "しょ!"
            else:
                print "ぽん!"
            time.sleep(1.0)
            for i in range(len(player_list)):
                print "%s:%s" % (player_list[i].get_name(), hand_print_dict[phand[i]])
            time.sleep(1.0)
            
            # ジャンケン勝敗判定
            flg_draw = self.judge_rps(player_list, phand)
            if flg_draw: continue
            
            # 勝敗メッセージ
            for i in range(len(player_list)):
                print "%s:%s勝" % (player_list[i].get_name(), player_list[i].get_win_count())
            time.sleep(1.0)

        
    # 目標勝数に到達したか判定
    def judge_max_win_count(self, player_list):
        win_count_max = 0
        for p in player_list:
            win_count_max = max(win_count_max, p.get_win_count())
        return win_count_max >= self.win_count_goal
    
    # ジャンケン勝敗判定
    def judge_rps(self, player_list, phand):
        # とりあえず2人限定で動くロジックで実装
        # TODO: 複数人対応
        # TODO: メッセージ切り出し
        if (3 + phand[0] - phand[1]) % 3 == 2:   # 勝ち
            flg_draw = False
            player_list[0].add_win_count()
            print "あなたの勝ちです。"
            time.sleep(1.5)
        elif (3 + phand[0] - phand[1]) % 3 == 1:  # 負け
            flg_draw = False
            player_list[1].add_win_count()
            print "あなたの負けです。"
            time.sleep(1.5)
        else:
            flg_draw = True
            print "あいこです。"
            time.sleep(1.5)
        return flg_draw
    

class Player:
    
    def __init__(self, name, strategy):
        self.name      = name
        self.strategy  = strategy
        self.hand      = 1
        self.win_count = 0
    
    # 手の決定
    def decide_hand(self):
        if self.strategy == 0:  # ユーザーの入力待ち
            self.hand = self.input_user_hand()
        elif self.strategy == 1:  # ランダムに手を決定
            self.hand = random.randint(1, 3)
        else:
            raise
    
    # 手を返す
    def get_hand(self):
        return self.hand

    # 勝ち数を返す
    def get_win_count(self):
        return self.win_count
    
    # 名前を返す
    def get_name(self):
        return self.name
    
    # 勝ち数を追加する
    def add_win_count(self):
        self.win_count += 1
    
    # ユーザーの手の入力
    def input_user_hand(self):
        phand_txt = raw_input("(何を出しますか?) (グー:r チョキ:s パー:p) > ")
        if phand_txt not in ("r", "s", "p"):
            phand = 0
            print "不正な文字です。"
            time.sleep(1.5)
        else:
            phand = hand_dict[phand_txt]
        
        return phand



# 初期化
flg_draw = False
player_list = []
player_list.append(Player("あなた", 0))
player_list.append(Player("あいて", 1))
game_rps = GameRPS()
game_rps.start_game_rps(player_list)

# 勝敗判定
if player_list[0].get_win_count() > player_list[1].get_win_count():
    print "%s勝%s敗であなたの勝ちです。" % (player_list[0].get_win_count(), player_list[1].get_win_count())
    time.sleep(1.5)
else:
    print "%s勝%s敗であなたの負けです。" % (player_list[0].get_win_count(), player_list[1].get_win_count())
    time.sleep(1.5)

print "終わりです。"
time.sleep(1.5)