我需要編寫一個狀態monad,它也可以支持錯誤處理。我正在考慮使用Either monad來達到這個目的,因爲它也可以提供有關導致錯誤的詳細信息。我找到了使用Maybe monad的狀態monad的定義,但是我無法修改它來使用Either而不是Maybe。以下是代碼:如何編寫一個執行錯誤處理的狀態monad?
newtype StateMonad a = StateMonad (State -> Maybe (a, State))
instance Monad StateMonad where
(StateMonad p) >>= k = StateMonad (\s0 -> case p s0 of
Just (val, s1) -> let (StateMonad q) = k val in q s1
Nothing -> Nothing)
return a = StateMonad (\s -> Just (a,s))
data State = State
{ log :: String
, a :: Int}
我沒有看到第一個代碼塊和第二個代碼塊之間的區別。你是否錯誤地包含了相同的代碼兩次,或者,如果不是,你能澄清它們之間的區別嗎? – seh 2010-10-31 15:57:34
@seh,良好的捕獲,它的更新 – 2010-10-31 16:07:42
還要注意,這兩個在操作上有點不同。 第二個版本允許可恢復的錯誤,而第一個版本終止於第一個錯誤。如果您正在建模日誌記錄,請注意第一個版本也會「失去」登錄錯誤。 – 2010-10-31 16:26:11