簡體   English   中英

管理,定相,組合monad的資源(在Scala或Haskell中)

[英]Resources on managing, phasing, composing monads (in Scala or Haskell)

我正在尋找資源討論組成monad的良好實踐。 我最緊迫的問題是我正在編寫一個系統,該系統正在使用一系列狀態monad而不是不同的狀態類型,似乎處理這種情況的最好方法就是創建一個大的產品類型(可能是prettied)即使第1階段對組件B不感興趣,第2階段僅對組件A.1感興趣,也包括我感興趣的所有組件。

在這類領域編寫代碼時,我非常感謝能夠很好地討論替代方案。 我自己的代碼庫是在Scala中,但我很高興閱讀有關Haskell中相同問題的討論。

使用StateT堆棧有點困難,因為當你寫入getput時,你正在談論哪一層會讓人感到困惑。 如果你在transformers風格中使用顯式堆棧,那么你必須使用一堆lift ,如果你使用mtl的基於類的方法,你會完全陷入困境。

-- using transformers explicit stack style
type Z a = StateT Int (StateT String IO) a

go :: Z ()
go = do int <- get
        str <- lift get
        replicateM int (liftIO $ putStrLn str)

我們可能希望避免使用明確的產品類型的狀態。 因為我們最終從我們的產品狀態,各個組件的功能可以很容易地get到使用這些單個組件gets

data ZState = ZState { int :: Int, str :: String }
type Z a = StateT ZState IO a

go :: Z ()
go = do i <- gets int
        s <- gets str
        replicateM i (liftIO $ putStrLn s)

但這可能被認為是丑陋仍有兩個原因:(1) put和修改一般沒有任何地方幾乎一樣好的故事和(2)我們不能輕易看到影響的功能的類型,比如說, int狀態並知道它不接觸str 我們更喜歡保持這種類型保證的模塊化。

如果你是lens那就是一個名為zoom的解決方案

-- the real type is MUCH more general
zoom :: Lens' mother child -> StateT child m a -> StateT mother m a 

它將某個較大狀態空間的子部分上的有狀態計算“提升”到整個狀態空間。 或者,實際上,我們像這樣使用它:

data ZState = ZState { _int :: Int, _str :: String }
makeLenses ''ZState

type Z = StateT ZState IO a

inc :: MonadState Int m => m ()
inc = modify (+1)

yell :: MonadState String m => m ()
yell = modify (map toUpper)

go :: Z ()
go = do zoom int $ do inc
                      inc
                      inc
        zoom str yell
        i <- use int
        s <- use str
        replicateM i (liftIO $ putStrLn s)

現在大多數問題都應該消失了 - 我們可以zoom以隔離有狀態操作,這些操作僅依賴於整個狀態的子集,如incyell並確定它們在類型中的隔離。 我們還可以使用useget內部狀態組件。

除此之外, zoom還可用於zoom深埋在各種變壓器堆棧內的狀態。 在這種情況下,完全通用類型可以正常工作

type Z a = EitherT String (ListT (StateT ZState IO)) a

>>> :t zoom int :: EitherT String (ListT (StateT Int IO)) a -> Z a
zoom int :: EitherT String (ListT (StateT Int IO)) a -> Z a

雖然這非常好,但完全通用的zoom需要一些繁重的技巧,你只能放大一些變壓器層。 (今天我很不清楚你如何將這個功能添加到你自己的圖層,盡管可能是這樣。)

暫無
暫無

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

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