テニスの勝負判定コード
キミのコードが汚い理由 - ITmedia エンタープライズ
Javaのコードは修正後もちっとも美しさを感じなかったのでスルーしていたのですが、美しいコード? - sshi.ContinualのRubyのコードが美しく感じたので、僕もHaskellに移植してみました。Rubyのコードは副作用がある部分が分離されているので、Haskellに移植するのが楽でした。ちょっと前までは副作用なんて全然気にせずにコードを書いていたのですが、Haskellを使うようになって、とても気にするようになりました(というか気にしないと、Haskellらしいまともなプログラムが書けないような)。
module Main (main) where import System (getArgs) type Player = (String, Int) data Result = Win | Lead | Tie deriving (Eq, Show) judgeTennisGame :: Player -> Player -> (Result, Player, Player) judgeTennisGame playerA @ (_, gameA) playerB @ (_, gameB) = (result leader loser, leader, loser) where (leader, loser) | gameA > gameB = (playerA, playerB) | otherwise = (playerB, playerA) result leader @ (_, gameLeader) loser @ (_, gameLoser) | gameLeader == gameLoser = Tie | gameLeader == 7 = Win | gameLeader == 6 && gameLoser < 5 = Win | otherwise = Lead showTennisGameResult :: (Result, Player, Player) -> String showTennisGameResult (result, (nameLeader, gameLeader), (_, gameLoser)) | result == Win = nameLeader ++ " wins the set " ++ score | result == Lead = nameLeader ++ " leads " ++ score | result == Tie = "Set is tied at " ++ show gameLeader | otherwise = error "not reach here." where score = show gameLeader ++ " - " ++ show gameLoser main :: IO () main = do args <- getArgs putStrLn $ showTennisGameResult $ judgeTennisGame ("PlayerA", (read $ args !! 0)) ("PlayerB", (read $ args !! 1))