From 561df60b57c0d53bb267b58e2575840846f7633a Mon Sep 17 00:00:00 2001 From: Sasha Date: Thu, 1 Feb 2018 12:24:07 +0100 Subject: [PATCH] Start implementing yakus --- KoiKoi.hs | 42 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/KoiKoi.hs b/KoiKoi.hs index 248b08c..8e1c446 100644 --- a/KoiKoi.hs +++ b/KoiKoi.hs @@ -1,15 +1,57 @@ module KoiKoi where import CCard +import Data.Bits (popCount, (.&.)) + +type Points = Int data Player = Player { hand :: Pack , captured :: Pack + , scored :: [Yaku] } data State = State { players :: (Player, Player) , river :: Pack , deck :: [ Card ] + , month :: Flower , turn :: Bool } + +data Yaku = + Goko + | Shiko + | AmeShiko + | Sanko + | InoShikaCho + | Tane + | Akatan + | Aotan + | Tan + | Kasu + | TsukimiZake + | HanamiZake + +yakus :: [ Pack -> Maybe (Yaku, Points) ] +yakus = [ + (\p -> lightsYaku (popCount p) (p `contains` RainMan)) . (lights .&.) + , is inoshikacho InoShikaCho + , moreThan 4 animals Tane + , is poetry Akatan + , is blue Aotan + , moreThan 4 ribbons Tan + , moreThan 9 plain Kasu + , is (set [SakeCup, FullMoon]) TsukimiZake + , is (set [SakeCup, CampCurtain]) HanamiZake + ] + where + lightsYaku 5 _ = Just (Goko, 10) + lightsYaku 4 hasRainMan = if hasRainMan then Just (AmeShiko, 7) else Just (Shiko, 8) + lightsYaku n hasRainMan = if not hasRainMan && n > 2 then Just (Sanko, 8) else Nothing + moreThan points set yaku = + threshold yaku . (\x -> x - points) . popCount . (set .&.) + threshold yaku n + | n > 0 = Just (yaku, n) + | otherwise = Nothing + is set yaku pack = if set == pack then Just (yaku, 5) else Nothing