2014-02-27 53 views
2

我正在嘗試編寫一個具有FFI到C的程序。有一種方法需要在指針上調用,該指針不返回任何內容。我的指針是RWS monad中的一個狀態,但是當我嘗試更改狀態時,由於惰性,函數不會被調用。我如何確保函數被調用?Haskell:如何在RWS monad中製造副作用嚴格

例如,在下面的代碼中,我如何顯示「創建外部monad」?

{-# LANGUAGE GeneralizedNewtypeDeriving #-} 
module Main where 

import Control.Monad.RWS.Strict 

newtype OuterMonad a = OuterMonad { 
    unwrapOuterMonad :: RWST()()() IO a 
} deriving (Monad, MonadIO) 


createOuterMonad :: OuterMonad() 
createOuterMonad = do 
    liftIO $ putStrLn "creating outer monad" 
    return() 

runOuterMonad :: OuterMonad a -> IO() 
runOuterMonad _ = putStrLn "RunOuterMonad!!" 

main :: IO() 
main = do 
    putStrLn "starting Program" 
    runOuterMonad $ do 
     createOuterMonad 

回答

3

你應該在某些時候OuterMonad評估。例如:

runOuterMonad :: OuterMonad a -> IO() 
runOuterMonad m = do 
    evalRWST (unwrapOuterMonad m)()() 
    putStrLn "RunOuterMonad!!" 
+1

'liftIO',雖然沒有錯,但這裏不需要,因爲'runOuterMonad'的結果類型只是'IO()'。 – kosmikus

+0

@ kosmikus,你是對的,我很習慣在處理monad變換器時寫'liftIO',我甚至都沒有意識到我在輸入它。 –

+0

這樣一個愚蠢的錯誤。感謝您指出。 – Akshat