Haskell练习Mooc FI Do符号
Haskell Exercise Mooc FI Do notation
的练习
-- Ex 5: define the IO operation readUntil f, which reads lines from
-- the user and returns them as a list. Reading is stopped when f
-- returns True for a line. (The value for which f returns True is not
-- returned.)
--
-- Example in GHCi:
-- *Set11> readUntil (=="STOP")
-- bananas
-- garlic
-- pakchoi
-- STOP
-- ["bananas","garlic","pakchoi"]
readUntil :: (String -> Bool) -> IO [String]
readUntil f = todo
你能给我提供一个使用 do 表示法的提示/解决方案吗?
我刚开始使用 do 表示法,目前“条件逻辑”和循环对我来说太复杂了。
非常感谢
仅使用 do-notation 和条件语句,我找到了以下解决方案:
readUntil :: (String -> Bool) -> IO [String]
readUntil f = do x <- getLine;
if f x then (return []) else (do xs <- readUntil f
return (x : xs))
函数首先从prelude中读取一行getLine
,然后检查(f x)
是否为真。然后 return 只是一个空列表。我们不能只写 ... if f x then [] ...
,因为 []
的类型不是 IO [String]
,而是 [String]
。要使 []
成为 IO [String]
类型,我们可以使用函数 return
或 pure
但使用 do-notation 我使用 return
函数,因为它包含在Monad
类型类。
如果 f x
等于 False
,那么我们将使用第二个 do-block 一次又一次地递归调用该函数,直到我们得到一个输入,其中 f x == True
因此 return 是空的列表。 do-notation 是必需的,因为 xs 必须具有类型 [String]
,但 readUntil
具有类型 IO [String]
。我们不能对类型为 IO String
的对象使用 :
(“缺点”)运算符,因此无法生成我们想要的列表。然后,我们将 x 添加到所有其他输入的列表 xs 中并 return 它。
对于函数 readUntil
的更通用版本,它能够与任何 monad 而不仅仅是 IO
Monad 一起工作,请参阅 Will Ness
的评论
-- Ex 5: define the IO operation readUntil f, which reads lines from
-- the user and returns them as a list. Reading is stopped when f
-- returns True for a line. (The value for which f returns True is not
-- returned.)
--
-- Example in GHCi:
-- *Set11> readUntil (=="STOP")
-- bananas
-- garlic
-- pakchoi
-- STOP
-- ["bananas","garlic","pakchoi"]
readUntil :: (String -> Bool) -> IO [String]
readUntil f = todo
你能给我提供一个使用 do 表示法的提示/解决方案吗? 我刚开始使用 do 表示法,目前“条件逻辑”和循环对我来说太复杂了。
非常感谢
仅使用 do-notation 和条件语句,我找到了以下解决方案:
readUntil :: (String -> Bool) -> IO [String]
readUntil f = do x <- getLine;
if f x then (return []) else (do xs <- readUntil f
return (x : xs))
函数首先从prelude中读取一行getLine
,然后检查(f x)
是否为真。然后 return 只是一个空列表。我们不能只写 ... if f x then [] ...
,因为 []
的类型不是 IO [String]
,而是 [String]
。要使 []
成为 IO [String]
类型,我们可以使用函数 return
或 pure
但使用 do-notation 我使用 return
函数,因为它包含在Monad
类型类。
如果 f x
等于 False
,那么我们将使用第二个 do-block 一次又一次地递归调用该函数,直到我们得到一个输入,其中 f x == True
因此 return 是空的列表。 do-notation 是必需的,因为 xs 必须具有类型 [String]
,但 readUntil
具有类型 IO [String]
。我们不能对类型为 IO String
的对象使用 :
(“缺点”)运算符,因此无法生成我们想要的列表。然后,我们将 x 添加到所有其他输入的列表 xs 中并 return 它。
对于函数 readUntil
的更通用版本,它能够与任何 monad 而不仅仅是 IO
Monad 一起工作,请参阅 Will Ness