17

我正在使用 Parsec 解析表达式,并且我想使用 Parsec 中的用户状态来跟踪这些表达式中的变量。不幸的是,我真的不知道该怎么做。

给定以下代码:

import Data.Set as Set
inp = "$x = $y + $z"

data Var = V String

var = do char '$'
      n <- many1 letter
      let v = Var n
       -- I want to modify the set of variables here
      return v

parseAssignment = ... -- parses the above assignment

run = case runIdentity $ runParserT parseAssignment Set.empty "" inp of
                   Left err -> ...
                   Right -> ...

因此,uinParsecT s u m a将是Set.Set. 但是我将如何将状态更新集成到 中var

我尝试了类似的东西modify $ Set.insert v,但这不起作用,因为Set.Set它不是状态单子。

4

2 回答 2

17

不幸的是,Yuras 的建议updateParserState并不是最优的(如果您也想修改 Parsec 的内部状态您可以使用该功能);相反,您应该将一个适用于您的自定义用户状态(即 type u -> u)的函数传递给modifyState,例如在此示例中:

expr  = do
  x <- identifier
  modifyState (+1)
  -- ^ in this example, our type u is Int
  return (Id x)

或使用getStateputState函数的任意组合。对于您的情况,您可以执行以下操作:

modifyState (Set.insert v)

有关更多信息,请参阅此链接

有关在 Parsec 中使用用户状态的更多类似教程的介绍,该文档虽然旧,但应该是相关的。

于 2011-06-25T13:10:57.027 回答
1

您可以使用updateParserState

于 2011-06-25T12:35:00.343 回答