我刚刚开始学习Haskell,但是现在没有循环是无限令人沮丧的。我想出了如何为函数编写循环。然而,我的问题是我想在迭代循环时输出一些结果。似乎我必须使用debug来执行这个简单的任务。
所以现在我想了解一个如何在主结构中打印10次字符串的例子。
换句话说,我想这样做10次:
main = do
putStrLn "a string"
感谢。我觉得这对我的任务非常有启发性。
答案 0 :(得分:45)
你可以定义一个递归函数,打印“一个字符串”n次(n是函数的参数),如下所示:
printStringNTimes 0 = return ()
printStringNTimes n =
do
putStrLn "a string"
printStringNTimes (n-1)
main = printStringNTimes 10
更通用的方法是定义一个重复任何IO动作n次的函数:
repeatNTimes 0 _ = return ()
repeatNTimes n action =
do
action
repeatNTimes (n-1) action
main = repeatNTimes 10 (putStrLn "a string")
上述功能已存在Control.Monad
名称replicateM_
下。
答案 1 :(得分:31)
当你刚刚开始时,Haskell的IO有点棘手,因为它基于monad。
您的问题虽然有一个简单的解决方案:
main = replicateM_ 10 $ putStrLn "a string"
这是使用replicateM_
Control.Monad
它有很多用于编写和执行monadic动作的有用函数。
答案 2 :(得分:1)
我也是Haskell的初学者,我的解决方案不那么优雅,但实用性很强。
main = do
putStr result
where
string = "a string"
result = concat [string ++ "\n" | i <- [1,2..10]]
所以在这里,我们定义了一个列表,其中的元素是要打印的字符串,后跟一个新的行字符。
答案 3 :(得分:1)
我认为执行for循环的最必要方法是:
for list action = mapM_ action list
main :: IO Int
main = do
for [0..10] (\ i -> do
print(i^2)
)
return 0
在我看来,这实际上很像C代码。
答案 4 :(得分:0)
执行类似的操作可使您循环播放特定功能,从而使其更具可重用性(而不是为要循环播放的每个新内容将其写出来)。
loop :: Int -> (IO()) -> IO()
loop 0 _ = return ()
loop n f =
do
f
loop (n - 1) f
示例:
main = do
loop 5 (do
putStr "hello "
putStrLn "there")
main = do
loop 3 (do
loop 4 (putStrLn "Hi")
putStrLn ""
)