簡體   English   中英

如何在Haskell中組合monad?

[英]How do I combine monads in Haskell?

特別是,我需要能夠將CGI monad與IO monad結合起來,但是如何將IO monad與Maybe monad相結合的示例可能會更好......

我假設你想使用Maybe monad提前終止(比如在C中breakreturn )。

在這種情況下,你應該使用MaybeT從MaybeT包( cabal install MaybeT )。

main = do
  runMaybeT . forever $ do
    liftIO $ putStrLn "I won't stop until you type pretty please"
    line <- liftIO getLine
    when ("pretty please" == line) mzero
  return ()

MaybeT是monad的monad變換器版本。

Monad變形金剛“為其他monad添加功能”。

你沒有確切地說你想要如何組合IOMaybe ,但是我假設你有許多函數可以返回你想要輕松組合的IO (Maybe a) 基本上你想把IO (Maybe a)作為一個獨立的類型用它自己的Monad實例來對待:

newtype IOMaybe a = IOM (IO (Maybe a))

-- "unpack" a value of the new type
runIOMaybe :: IOMaybe a -> IO (Maybe a)
runIOMaybe (IOM a) = a

instance Monad IOMaybe where
   -- bind operator
   (IOM ioa) >>= f = IOM $ do
      a <- ioa
      case a of
         Nothing -> return Nothing
         Just v  -> runIOMaybe (f v)

   -- return
   return a = IOM (return (Just a))

-- maybe also some convenience functions
returnIO :: IO a -> IOMaybe a
returnIO ioa = IOM $ do
   v <- ioa
   return (Just v)

returnMaybe :: Maybe a -> IOMaybe a
returnMaybe ma = IOM (return ma)

有了這個,您可以使用do -otation來組合返回IO (Maybe a)IO a或者Maybe a函數:

f1 :: Int -> IO (Maybe Int)
f1 0 = return Nothing
f1 a = return (Just a)

main = runIOMaybe $ do
   returnIO $ putStrLn "Hello"
   a <- returnMaybe $ Just 2
   IOM $ f1 a
   return ()

通常,組合和修改這樣的monad的東西稱為monad變換器 ,GHC附帶一個包含monad變換器的 ,用於常見情況。 如果此monad變換器庫中有適合您的場景的內容取決於您希望如何組合Maybe和IO。

在什么意義上你想組合monad?

f :: Int -> IO (Maybe Int)
f x = do
    putStrLn "Hello world!"
    return $ if x == 0 then Nothing else Just x

可以評估為:

[1 of 1] Compiling Main             ( maybe-io.hs, interpreted )
Ok, modules loaded: Main.
*Main> f 0
Hello world!
Nothing
*Main> f 3
Hello world!
Just 3

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM