[英]Generating lists in a monadic context
據我了解,您可以在haskell中使用'draw from' (<-)
關鍵字從do-notation中的一元上下文中獲取值:
func = do
x <- getRandom
let y = (x + 1)
return y
生成列表時如何應用? 假設我正在映射一個函數f :: (MonadRandom m) => Int -> ma
,它接受一個整數並在MonadRandom
上下文中返回一個值。 我想在MonadRandom
上下文即m [a]
生成類型為a
的值的列表。 我相信這樣做是這樣的:
func = do
xs <- map f [0..10]
return xs
會生成一個值列表,每個值都在單子上下文中,然后嘗試從不在MonadRandom
上下文中的列表中進行繪制
抱歉,如果我的術語/理解不正確,我是Haskell的新手。
對於MonadRandom的編輯,我認為您需要的只是mapM
:
import System.Random (randomRIO)
f :: Int -> IO Int
f n = randomRIO (n,n+n)
g :: [Int] -> IO [Int]
g xs = mapM f xs
例
λ> g [1..3]
[1,4,5]
λ> g [1..3]
[1,3,4]
λ> g [1..3]
[1,4,6]
順便說一句:當然,您可以使用do
自己執行此do
:
g :: [Int] -> IO [Int]
g [] = return []
g (x:xs) = do
r <- f x
rs <- g xs
return (r:rs)
只是要記住不要在此處將列表和IO
monad混合在一起-因此, do
, <-
和此處return
在IO
-對於此答案的其余部分,它將在list-monad中
首先,您的示例(如果f :: a -> [b]
)將創建一個值列表的列表 (您肯定已經發現了)-如果您想將其展平到下面(基本上,您只需再次拉出) )
目前,我還不清楚您要去哪里,但是這里有一個簡短的示例,說明如何將do
符號與列表一起使用:
看一下這個功能:
combs :: [a] -> [b] -> [(a,b)]
combs xs ys = do
x <- xs
y <- ys
return (x,y)
這是一個實際的例子:
λ> combs [1..3] "Hi"
[(1,'H'),(1,'i'),(2,'H'),(2,'i'),(3,'H'),(3,'i')]
正如你所看到的, 關鍵是要畫一個例子 x
掉所有的xs
(你當然會盡一切-所以你可以認為這與組合數學工作)和y
出來的ys
,然后做他們的東西(這里只是做一個元組),最后return
它。
現在,您當然可以先以某種方式對其進行映射了(這里只需將xs
加倍):
combs :: [a] -> [b] -> [(a,b)]
combs xs ys = do
x <- xs ++ xs
y <- ys
return (x,y)
它將拉出映射的值:
λ> combs [1..3] "Hi"
[(1,'H'),(1,'i'),(2,'H'),(2,'i'),(3,'H'),(3,'i'),(1,'H'),(1,'i'),(2,'H'),(2,'i'),(3,'H'),(3,'i')]
這對您有幫助嗎?
這是f
本身創建列表的另一個:
func :: (a -> [b]) -> [a] -> [b]
func f xs = do
x <- xs
b <- f x
return b
如您所見,首先我們從xs
拉出一個x
,應用f
來獲得b
s的列表,然后只用b <- fx
將它們拉出,然后返回它們。
當然,這只是concatMap
λ> func (\x -> [x,x]) [1..5]
[1,1,2,2,3,3,4,4,5,5]
這是您要去的地方嗎?
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.