镜头访问Map Key

问题描述 投票:2回答:1

使用Lens库访问Map Data类型时遇到一些问题。

data Card
  = Ferme
  | Boulangerie

data PlayerState = PlayerState {
  _psCards      :: Map Card Int,
  } deriving (Show)


data GameState = GameState {
  _gsPlayers      :: [PlayerState]
                 } deriving (Show)

我很难进入Map

step :: (MonadState s m, HasGameState s, MonadIO m) => m ()
step = do
    i <- use $ gsPlayers . ix 0 . psCards . ix Ferme

出现以下错误:

    • Could not deduce (Monoid Int) arising from a use of ‘ix’
      from the context: (MonadState s m, HasGameState s, MonadIO m)
        bound by the type signature for:
                   step :: forall s (m :: * -> *).
                           (MonadState s m, HasGameState s, MonadIO m) =>
                           m ()

这是因为我在同一行使用不同参数的ix吗?

haskell lens
1个回答
3
投票

这是因为ix是一个Traversal,但use期待一个镜头。不同之处在于镜头始终只有一个目标。遍历可以为零或更多。在检索值时,期望镜头的组合器意外地尝试将多个值组合在一起作为Monoid,当给定遍历时。 (它特别来自ApplicativeConst实例。)该尝试不会在您的情况下键入check,因为目标类型不存在此类实例,因此您会收到该错误消息。

您可能希望使用preuse组合器而不是use来计算可能不存在的值。

© www.soinside.com 2019 - 2024. All rights reserved.