Haskell - 做while循环

Posted

技术标签:

【中文标题】Haskell - 做while循环【英文标题】:Haskell - Do while loop 【发布时间】:2016-06-08 22:44:23 【问题描述】:

我是 Haskell 的新手,如果有人愿意帮助我,我会很高兴!我试图让这个程序与 do while 循环一起工作。

第二个 getLine 命令的结果被放入变量 goGlenn 中,如果 goGlenn 不等于 "start" 则程序将返回到开头

    start = do
    loop $ do lift performAction
        putStrLn "Hello, what is your name?"
        name <- getLine
        putStrLn ("Welcome to our personality test " ++ name ++ ", inspired by the Big Five Theory.") 
        putStrLn "You will receive fifty questions in total to which you can reply with Yes or No."
        putStrLn "Whenever you feel ready to begin please write Start"
        goGlenn <- getLine
        putStrLn goGlenn
    while (goGlenn /= "start")

【问题讨论】:

补充@chi 的答案,您编写的代码或多或少是正确的Haskell 语法,但没有内置loopwhile 之类的东西。Haskell 没有t 实际上有 do-while 循环,它具有可用于实现 do-while 循环的递归。 Haskell 实际上根本没有循环,只有递归,您必须学习如何从您使用的命令式语言中重新实现功能。 @bheklilr 我猜加莱在他们下面的评论中是对的:上面的代码似乎改编自 Control.Monad.LoopWhile 文档。 【参考方案1】:

在 Haskell 中,大多数时候你会递归地编写“循环”。

import Control.Monad

-- ....

start = do
    putStrLn "Before the loop!"
    -- we define "loop" as a recursive IO action
    let loop = do
            putStrLn "Hello, what is your name?"
            name <- getLine
            putStrLn $ "Welcome to our personality test " ++ name 
                     ++ ", inspired by the Big Five Theory."
            putStrLn "You will receive fifty questions in total to which you can reply with Yes or No."
            putStrLn "Whenever you feel ready to begin please write Start"
            goGlenn <- getLine
            putStrLn goGlenn
            -- if we did not finish, start another loop
            when (goGlenn /= "start") loop
    loop  -- start the first iteration 
    putStrLn "After the loop!"

【讨论】:

我猜 OP 正在尝试使用loop-while(请参阅与代码摘录的相似性)。查看导入列表会有所帮助。 @gallais 有趣,我不知道...不过,我想知道 OP 是否真的想使用该库,或者只是想达到相同的效果。对于初学者,我建议先学习基本方法。 不写let loop = ...; loop,我更喜欢写fix $ \loop -&gt; ...。当然,这纯粹是风格。【参考方案2】:

不确定,也许这个版本可以帮助你:

import Control.Monad

loop action = do
    condition <- action
    when condition (loop action)

while = return

start =
    let action = do 
        putStrLn "Hello, what is your name?";
        name <- getLine;
        putStrLn ("Welcome to our personality test " ++ name ++ ", inspired by the Big Five Theory.");
        putStrLn "You will receive fifty questions in total to which you can reply with Yes or No.";
        putStrLn "Whenever you feel ready to begin please write Start";
        goGlenn <- getLine;
        putStrLn goGlenn;
        while (goGlenn /= "start");
    
    in loop action

(编辑)或者也可以:

start =
    loop (do 
        putStrLn "Hello, what is your name?";
        name <- getLine;
        putStrLn ("Welcome to our personality test " ++ name ++ ", inspired by the Big Five Theory.");
        putStrLn "You will receive fifty questions in total to which you can reply with Yes or No.";
        putStrLn "Whenever you feel ready to begin please write Start";
        goGlenn <- getLine;
        putStrLn goGlenn;
        while (goGlenn /= "start");
    )        

【讨论】:

如果我们定义一个自定义辅助函数loop,我会想内联action的定义并直接写loop $ do ... 但是没有问题...(我认为是这样)请检查答案中的编辑 是的,两种方式都是正确的。第二个更好,至少对我来说。

以上是关于Haskell - 做while循环的主要内容,如果未能解决你的问题,请参考以下文章

不能写成 for 循环的 while 循环示例

text 做while while循环

流程控制之while循环

while循环和for循环

while循环和for循环

流程控制之while循环