Haskell 自己的复制项实现

Haskell 自己的复制项实现,haskell,Haskell,我想知道是否可以为Bool编写自己的replicItem实现 没有导入Monad模块的值?当我查看Haskell源代码时,它看起来确实很复杂,但我想知道该函数是如何工作的,它应该是什么样子。实现replicateM的一种方法是: replicateM n = sequence . replicate n 这有助于你的理解吗?当然,棘手的部分在于序列的操作,它有以下有趣的类型: sequence :: Monad m => [m a] -> m [a] 因此, replicateM

我想知道是否可以为Bool编写自己的replicItem实现
没有导入Monad模块的值?当我查看Haskell源代码时,它看起来确实很复杂,但我想知道该函数是如何工作的,它应该是什么样子。

实现
replicateM
的一种方法是:

replicateM n = sequence . replicate n
这有助于你的理解吗?当然,棘手的部分在于
序列的操作,它有以下有趣的类型:

sequence :: Monad m => [m a] -> m [a]
因此,

replicateM 3 (Just 1) 
  = sequence (replicate 3 (Just 1))
  = sequence ([Just 1, Just 1, Just 1])
  = Just [1,1,1]

replicItem
的定义是:

replicateM n x = sequence (replicate n x)
Monad m => [m a] -> m [a]
sequence ms = foldr k (return []) ms
            where
              k m m' = do { x <- m; xs <- m'; return (x:xs) }
replicate
具有类型
Int->a->[a]
,因此,例如
replicate 4 True
就是
[True,True,True,True]

对于列表参数
l=[True,False]
replicate 2 l
[[True,False],[True,False]
。您的评论询问
replicate
replicateM
之间有什么不同,您可以看到
replicateM
使用
replicate
,但随后对结果调用
sequence

序列的类型为:

replicateM n x = sequence (replicate n x)
Monad m => [m a] -> m [a]
sequence ms = foldr k (return []) ms
            where
              k m m' = do { x <- m; xs <- m'; return (x:xs) }
在本例中,
m
是列表,因此它将列表列表转换为另一个列表列表。 正如您所指出的,结果不同于调用
replicate 2l
。序列的定义是:

replicateM n x = sequence (replicate n x)
Monad m => [m a] -> m [a]
sequence ms = foldr k (return []) ms
            where
              k m m' = do { x <- m; xs <- m'; return (x:xs) }
它是笛卡尔积,即,通过考虑累加器中每个列表前面的
m
元素,形成一个新列表


考虑列表的一种方法是对非确定性选择进行建模,因此结果是输入列表中
n
选择的所有可能结果。

我不是假装回答这个问题,但注释中缺少格式迫使我回答。 简短版本为
replicateM n m
相当于

m >>= (\x1 -> m >>= (\x2 -> ... m >>= ( \xn -> return [x1,x2,...,xn])..))
或类似

do 
  x1 <- m
  x2 <- m
  ...
  xn <- m
  return [x1,x2,...,xn]
do

x1
Bool
不是单子,所以您可以使用
replicate
。但是
replicatem2[True,False]
返回的内容与
replicate 2[True,False]返回的内容不一样。
我不确定我是否理解问题陈述。你能清楚地说明为什么有一个“复杂”的实现对你来说是个问题,并且我们可以考虑什么样的标准来提供一个不那么复杂的替代实现。我们已经解决了您的问题?很简单-我只想知道它是如何工作的,因为我不清楚在
replicateM
中发生了什么,我很高兴看到它应该如何实现。我相信这会帮助我理解整个过程。我想你实际上很难理解单子列表。因为
replicitem 2[True,False]
正在列表monad中工作。列表中包含的
Bool
s在这里真的不相关>“当然,棘手的部分在于序列的操作,它有以下有趣的类型”我相信这个函数也没有那么棘手:它就像foldr1>>