使用 Parsec 解析 or-else 之前的空格
Parsing whitespace before or-else with Parsec
我正在使用 Haskell 中的 Parsec
模块来解析文件。这些文件的组成部分之一是颜色。我为这样的颜色创建了一个类型:
data Color = Yellow | Red | Blue | Green deriving (Show)
我最初尝试解析颜色是这样的:
symbol :: String -> Parsec String () String
symbol s = spaces >> string s
colorP :: Parsec String () Color
colorP =
liftM mkColor $ symbol "Yellow" <|> symbol "Red" <|> symbol "Blue" <|> symbol "Green"
where
mkColor :: String -> Color
mkColor "Yellow" = Yellow
mkColor "Red" = Red
mkColor "Blue" = Blue
mkColor "Green" = Green
我创建了 symbol
解析器,它基本上吃掉尽可能多的空格,然后吃掉给定的字符串 s
。但是,这似乎不起作用。我使用以下调用测试此代码:
parse colorP "" " Red"
这给了我以下错误:
unexpected "R"
expecting space or "Yellow"
但是,我继续在 Hoogle 上查找与 <|>
运算符一起使用的文档,并在那里找到了以下内容:
This combinator implements choice. The parser p <|> q first applies p. If it succeeds, the value of p is returned. If p fails without consuming any input, parser q is tried.
因此,我认为上述示例的问题在于解析器 p
(在本例中为 symbol "Yellow"
)已经消耗了一些输入,即空白!所以,我像这样重构了我的 colorP
:
colorP =
liftM mkColor $ spaces >> (string "Yellow" <|> string "Red" <|> string "Blue" <|> string "Green")
where
-- mkColor same as before
这给出了我想要的结果。
现在,我想知道是否没有像我编写的 symbol
解析器那样的解析器,但它会在出现故障时返回输入。或者 colorP
的第二个实现是最 Haskell-ish 的那个?
您可以使用 try
symbol s = try (spaces >> string s)
The parser try p behaves like parser p, except that it pretends that it hasn't consumed any input when an error occurs.
我正在使用 Haskell 中的 Parsec
模块来解析文件。这些文件的组成部分之一是颜色。我为这样的颜色创建了一个类型:
data Color = Yellow | Red | Blue | Green deriving (Show)
我最初尝试解析颜色是这样的:
symbol :: String -> Parsec String () String
symbol s = spaces >> string s
colorP :: Parsec String () Color
colorP =
liftM mkColor $ symbol "Yellow" <|> symbol "Red" <|> symbol "Blue" <|> symbol "Green"
where
mkColor :: String -> Color
mkColor "Yellow" = Yellow
mkColor "Red" = Red
mkColor "Blue" = Blue
mkColor "Green" = Green
我创建了 symbol
解析器,它基本上吃掉尽可能多的空格,然后吃掉给定的字符串 s
。但是,这似乎不起作用。我使用以下调用测试此代码:
parse colorP "" " Red"
这给了我以下错误:
unexpected "R"
expecting space or "Yellow"
但是,我继续在 Hoogle 上查找与 <|>
运算符一起使用的文档,并在那里找到了以下内容:
This combinator implements choice. The parser p <|> q first applies p. If it succeeds, the value of p is returned. If p fails without consuming any input, parser q is tried.
因此,我认为上述示例的问题在于解析器 p
(在本例中为 symbol "Yellow"
)已经消耗了一些输入,即空白!所以,我像这样重构了我的 colorP
:
colorP =
liftM mkColor $ spaces >> (string "Yellow" <|> string "Red" <|> string "Blue" <|> string "Green")
where
-- mkColor same as before
这给出了我想要的结果。
现在,我想知道是否没有像我编写的 symbol
解析器那样的解析器,但它会在出现故障时返回输入。或者 colorP
的第二个实现是最 Haskell-ish 的那个?
您可以使用 try
symbol s = try (spaces >> string s)
The parser try p behaves like parser p, except that it pretends that it hasn't consumed any input when an error occurs.