簡體   English   中英

Haskell - 我如何運行狀態monad列表?

[英]Haskell - How would I run a list of state monads?

我對Haskell有些新意,我在State monad遇到了一些麻煩。

我創建了以下類型。 Stat a具有為其創建的monoid,functor,applicative和monad實例。

我的程序中的“主”類型是生物,它有很多參數:

data Creature = Creature {
    strength  :: Stat Integer,
    dexterity :: Stat Integer,
    ...
}

data Stat a = Stat {
    modifiers :: [StatModifier],
    stat      :: a
}

data StatModifier = StatModifier {
    modifierType :: ModifierType,
    value        :: Integer
}

data ModifierType = 
  Enhancement
  | Morale
  | ...

生物有許多事情可能發生。 我選擇用州monad代表那些東西:

anyPossibleChange :: State Creature Creature

這可能是對生物造成的傷害,生物力量的增加,基本上是任何東西。 任何事情的可能性讓我覺得國家monad在這里是個不錯的選擇。 我將接受一個處於原始狀態的生物,執行一些修改,並將原始狀態和新狀態返回到元組中。

原始狀態可能是:

Creature {
    strength = Stat [] 10,
    dexterity = Stat [] 10
}

最終狀態可能是:

Creature {
    strength = Stat [StatModifier Enhancement 2] 10,
    dexterity = Stat [StatModifier Enhancement 4, StatModifier Morale 2] 10
}

我想建立一個生物需要經歷的所有變化的列表,然后通過所有這些變化運行該生物。

這是我想到的簽名,但是我在實現時遇到了麻煩。 我願意與眾不同。

applyChanges :: Creature -> [State Creature Creature] ->  Creature

我覺得我應該能夠用折疊來做這件事,可能是FoldM但我的大腦FoldM掛了。

好的實施是什么?

State Creature Creature是這種計算的錯誤類型。 如你所見,你可以逃脫它,但它會使事情變得不必要,因為你根本不關心狀態變量! 您只需使用它來存儲函數的原始輸入...但是然后將其丟棄在applyChanges

一個更容易使用的類型是Creature -> Creature ,然后如果你有一個這樣的函數列表要應用你只想組成它們,你可以用折疊做:

applyChanges :: [Creature -> Creature] -> Creature -> Creature
applyChanges = foldr (.) id

暫無
暫無

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

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