Added combination checks.
This commit is contained in:
parent
4210670e9e
commit
4939d5fb09
2 changed files with 110 additions and 0 deletions
86
poker_ex/lib/poker_ex/combination.ex
Normal file
86
poker_ex/lib/poker_ex/combination.ex
Normal file
|
|
@ -0,0 +1,86 @@
|
|||
defmodule PokerEx.Combination do
|
||||
alias __MODULE__
|
||||
alias PokerEx.Card, as: Card
|
||||
|
||||
@type score() ::
|
||||
:high_card
|
||||
| :pair
|
||||
| :two_pair
|
||||
| :three_of_a_kind
|
||||
| :straight
|
||||
| :flush
|
||||
| :full_house
|
||||
| :four_of_a_kind
|
||||
| :straight_flush
|
||||
| :royal_flush
|
||||
@type t() :: %Combination{score: score(), cards: [Card.t()]}
|
||||
defstruct score: :invalid, cards: []
|
||||
|
||||
def straight?(sorted_hand) do
|
||||
# Grab the ranks of the card, have a sliding window and check if the
|
||||
# difference between all cards is 1.
|
||||
|
||||
sorted_hand
|
||||
|> Enum.map(& &1.rank)
|
||||
|> Enum.map(
|
||||
&case &1 do
|
||||
:jack -> 11
|
||||
:queen -> 12
|
||||
:king -> 13
|
||||
:ace -> 14
|
||||
n -> n
|
||||
end
|
||||
)
|
||||
|> Enum.chunk_every(2, 1, :discard)
|
||||
|> Enum.map(
|
||||
&case &1 do
|
||||
[14, 2] -> 1 # Special case of A followed by a 2
|
||||
[a, b] -> b - a
|
||||
end
|
||||
)
|
||||
|> Enum.all?(& &1 == 1)
|
||||
end
|
||||
|
||||
def flush?(hand) do
|
||||
hand
|
||||
|> Enum.map(& &1.suit)
|
||||
|> Enum.frequencies()
|
||||
|> Map.values()
|
||||
|> Enum.any?(& &1 >= 5)
|
||||
end
|
||||
|
||||
def evaluate_hand(hand) do
|
||||
end
|
||||
|
||||
@doc ~S"""
|
||||
Finds the highest combination that can be made using the hand and the cards
|
||||
that are present.
|
||||
|
||||
## Examples
|
||||
|
||||
iex> PokerEx.Combination.find [%PokerEx.Card{suit: :diamonds, rank: 5}]
|
||||
{:ok, %PokerEx.Combination{score: :high_card, cards: [%PokerEx.Card{suit: :diamonds, rank: 5}]}}
|
||||
|
||||
iex> PokerEx.Combination.find [%PokerEx.Card{suit: :diamonds, rank: 5}, %PokerEx.Card{suit: :hearts, rank: :ace}]
|
||||
{:ok, %PokerEx.Combination{score: :high_card, cards: [%PokerEx.Card{suit: :hearts, rank: :ace}]}}
|
||||
|
||||
iex> comb = PokerEx.Combination.find [
|
||||
...> %PokerEx.Card{suit: :spades, rank: :king},
|
||||
...> %PokerEx.Card{suit: :spades, rank: :king},
|
||||
...> %PokerEx.Card{suit: :spades, rank: :king},
|
||||
...> %PokerEx.Card{suit: :spades, rank: :queen},
|
||||
...> %PokerEx.Card{suit: :spades, rank: :queen}
|
||||
...> ]
|
||||
iex> comb.score == :full_house
|
||||
true
|
||||
|
||||
iex> PokerEx.Combination.find []
|
||||
{:error, :invalid_list}
|
||||
|
||||
iex> PokerEx.Combination.find ["Hello"]
|
||||
{:error, :invalid_list}
|
||||
"""
|
||||
@spec find([Card.t()]) :: {:ok, Combination.t()} | {:error, atom}
|
||||
def find([%Card{suit: s, rank: :ace}]) do
|
||||
end
|
||||
end
|
||||
24
poker_ex/test/poker_ex/combination_test.exs
Normal file
24
poker_ex/test/poker_ex/combination_test.exs
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
defmodule PokerEx.CombinationTest do
|
||||
alias PokerEx.Combination
|
||||
import PokerEx.Card
|
||||
use ExUnit.Case
|
||||
|
||||
test "test straight" do
|
||||
hand = [~p"C2", ~p"C3", ~p"C4", ~p"C5", ~p"C6"]
|
||||
assert Combination.straight?(hand) == true
|
||||
|
||||
hand = [~p"C2", ~p"D3", ~p"S4", ~p"S5", ~p"C7"]
|
||||
assert Combination.straight?(hand) == false
|
||||
|
||||
hand = [~p"D10", ~p"SJ", ~p"HQ", ~p"CK", ~p"DA"]
|
||||
assert Combination.straight?(hand) == true
|
||||
|
||||
hand = [~p"SA", ~p"D2", ~p"H3", ~p"C4", ~p"S5"]
|
||||
assert Combination.straight?(hand) == true
|
||||
end
|
||||
|
||||
test "test flush" do
|
||||
assert Combination.flush?([~p"CA", ~p"C10", ~p"C2", ~p"CK", ~p"C5"]) == true
|
||||
assert Combination.flush?([~p"CA", ~p"C10", ~p"C2", ~p"CK", ~p"D5"]) == false
|
||||
end
|
||||
end
|
||||
Loading…
Add table
Reference in a new issue