0

假设我有这样的东西

main = do
    input_line <- getLine
    let n = read input_line :: Int

    replicateM n $ do
        input_line <- getLine
        let x = read input_line :: Int 

        return ()

 ***putStrLn $ show -- Can i access my replicateM here?
    return ()

我可以访问我的 replicateM 的结果,例如它是否是返回值,例如打印出来。或者我必须在实际的 do-block 中使用 replicateM 吗?

4

3 回答 3

4

专门从事IO

replicateM :: Int -> IO a -> IO [a]

这意味着它返回一个列表。所以在你的例子中你可以这样做:

results <- replicateM n $ do
    input_line <- getLine
    let x = read input_line :: Int
    return x   -- <- we have to return it if we want to access it

print results
于 2018-06-03T00:03:58.573 回答
3

replicateM n a返回由 . 返回的值的列表a。在您的情况下,这只是一个单位列表,因为return ()最后有,但是如果将其替换为return x,您将获得读取的整数列表。然后,您可以使用<-将其从IO.

您还可以使用readLine代替getLineand来简化代码read。同样putStrLn . show可以替换为print

main = do
    n <- readLn
    ints <- replicateM n readLn :: IO [Int]
    print ints
于 2018-06-03T00:03:47.907 回答
1

当然。它的类型是replicateM :: Monad m => Int -> m a -> m [a]. 这意味着它可以出现<-do块的右侧:

    do
        ....
        xs <- replicateM n $ do { ... }
        ....

xs将是 类型[a],通常用于绑定来自 的结果Monad m => m [a]

但是,使用您的代码,在return ()嵌套的中显示的位置do,您 ()nxs. 大概在真正的代码中,您会在那里找到return一些有用的东西。

于 2018-06-03T00:04:38.477 回答