LoginSignup
1

posted at

updated at

ポーカー判定 PHP

なんとなくポーカーの役を判定するコードを書いてみる。参考なし。最適化はしない。

<?php
define('SPADE', 0);
define('CLUB', 1);
define('HEART', 2);
define('DIAMOND', 3);
$suit = [SPADE, CLUB, HEART, DIAMOND];

// ランダムでカードを選択(重複は考慮しない)
$cards = array_map(fn() => [0 => array_rand($suit), 1 => random_int(0, 13)], range(1,5));

// 判定
$result = judge($cards);

// 出力
$mark = [SPADE=>"♠", CLUB=>"♣", HEART=>"♥", DIAMOND=>"♦"];
$c = array_map(fn($v) => $v[1]==0?'JOKER':$mark[$v[0]].$v[1], $cards);
echo implode(', ', $c) . " : ". $result . PHP_EOL;


function judge($cards) {
	$joker = 0; // JOKERの枚数
	foreach ($cards as $k => $card) {
		if ($card[1]==1) {
			$cards[$k][1] = 14; // 1 は 14 とする
		} else if ($card[1]==0) {
			// JOKERの場合、配列から削除
			unset($cards[$k]);
			$joker++;
		}
	}
	if ($joker==5) return "ロイヤルストレートフラッシュ";

	// スートと数字を分離
	$suit = array_column($cards, 0);
	$number = array_column($cards, 1);
	$max = max($number);
	$min = min($number);


	// フラッシュ判定
	$suit_count = array_count_values($suit); // スートの数
	$isFlush = (count($suit_count)==1);

	// 数字の数
	$number_count = array_count_values($number);
	// ペア数
	$pair = [1=>0,2=>0,3=>0,4=>0,5=>0];
	foreach ($number_count as $v) $pair[$v]++;

	// ストレート判定(ペアがなく、最小値と最大値の差が4以下)
	$isStraight = ($pair[1]==count($cards) && ($max - $min) <= 4);

	// 強い順に判定
	if ($isFlush && $isStraight && $min >= 10) {
		// jokerの枚数に関わらず min≧10 で判定可能
		return "ロイヤルストレートフラッシュ";
	} else if ($isFlush && $isStraight) {
		return "ストレートフラッシュ";
	} else if ($pair[5] == 1 // イカサマ
			|| $pair[4] == 1 && $joker == 1
			|| $pair[3] == 1 && $joker == 2
			|| $pair[2] == 1 && $joker == 3
			|| $joker >= 4) {
		return "ファイブカード";
	} else if ($pair[4] == 1
			|| $pair[3] == 1 && $joker == 1
			|| $pair[2] == 1 && $joker == 2
			|| $joker == 3) {
		return "フォーカード";
	} else if ($pair[2] == 1 && $pair[3] == 1
			|| $pair[2] == 2 && $joker == 1
			|| $pair[3] == 1 && $joker == 2) {
		return "フルハウス";
	} else if ($isFlush) {
		return "フラッシュ";
	} else if ($pair[1]==count($number) && $isStraight) {
		return "ストレート";
	} else if ($pair[3] == 1 || $pair[2] == 1 && $joker == 1 || $joker == 2) {
		return "スリーカード";
	} else if ($pair[2] == 2) {
		return "ツーペア";
	} else if ($pair[2] == 1 || $joker == 1) {
		return "ワンペア";
	} else {
		return "役なし";
	}
}

結果(何回か適当に)

♠1, ♦8, ♥8, ♠10, ♦11 : ワンペア
♣11, ♥10, ♥10, ♣10, ♥10 : フォーカード
JOKER, ♥1, ♥10, ♠1, ♣12 : スリーカード
♣10, ♠9, JOKER, ♣12, ♠10 : スリーカード
♥6, ♥7, ♣10, ♥8, JOKER : ストレート
♦4, ♥3, ♠6, ♠2, JOKER : ストレート
♠10, ♥11, ♠12, ♠13, JOKER : ストレート
♠9, ♠4, ♠11, ♠8, ♠2 : フラッシュ
♣11, ♠5, ♣5, JOKER, ♠11 : フルハウス
JOKER, JOKER, ♦13, JOKER, ♥3 : フォーカード
♠10, ♠11, ♠12, ♠13, ♠1 : ロイヤルストレートフラッシュ
JOKER, ♠11, ♠12, ♠13, ♠1 : ロイヤルストレートフラッシュ
♠9, ♠11, ♠12, ♠13, JOKER : ストレートフラッシュ

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
What you can do with signing up
1