Как отслеживать количество догадок в простой игре на угадывание (Haskell)

Последние несколько недель я пытался выучить Haskell самостоятельно. В настоящее время я пытаюсь реализовать глупую маленькую игру в угадайку, в которой компьютер выбирает случайное число, а пользователь пытается его угадать. Если пользователь ошибается, программа сообщает пользователю, что ответ выше или ниже, и позволяет пользователю угадывать, пока он не угадает правильно. У меня это работает, но я хотел бы добавить возможность отслеживать количество догадок, которые пользователь делает в каждой игре, и сообщать это число пользователю, когда он угадывает правильно.

Исходя из императивного фона, естественным было бы иметь счетчик, который увеличивается каждый раз, когда пользователь делает предположение, но вы не можете сделать это в Haskell (, по крайней мере, это похоже на отсутствие состояния и неизменность всего помешало бы этому ).

Я поиграл с идеей заставить функции getGuess и giveHints принимать дополнительный параметр, представляющий количество догадок на данный момент (, назовем его numGuesses ), и при каждом вызове этих методов передавать (numGuesses+ 1 ). Но я не мог заставить это работать (, не говоря уже о том, что я даже не знаю, сработает ли это ).

Мой код ниже. Любые предложения будут действительно оценены. В основном я ищу идеи, но не стесняйтесь публиковать и реальный код. Кроме того, не стесняйтесь, дайте мне знать, если мой код отстой, и как я могу его улучшить, если вы заметите что-нибудь ужасное (Я занимаюсь функциональным программированием всего пару недель!)

    import System.Random
    import System.IO
    import Control.Monad

    main = do
        gen <- getStdGen
        let (ans,_) = randomR (1,100) gen :: (Int,StdGen)
        putStrLn $ "I'm thinking of a number between 1 and 100..."
        getGuess ans
        putStrLn "You guessed it in __ guesses!"
        putStr "Play again? "
        hFlush stdout
        desire <- getLine
        when ((desire !! 0) `elem` ['y','Y']) $ do
            putStrLn ""
            newStdGen
            main

    getGuess ans = do   
        putStr "Your guess? "
        hFlush stdout
        guessStr <- getLine
        giveHints ans (read guessStr)

    giveHints ans guess = do
        when (ans /= guess) $ do
           if ans > guess 
               then putStrLn "It's higher." 
               else putStrLn "It's lower."
           getGuess ans

Примечание. :Я использую стандартный вывод hFlush, потому что я использую буферизацию строк, а без нее порядок некоторых взаимодействий не такой, как можно было бы ожидать.

7
задан mkfarrow 8 August 2012 в 00:43
поделиться