秒差距错误 - 尝试似乎不起作用
我目前正在使用 文本.Parsec.Expr 模块用于解析脚本语言的子集。
基本上,这种语言有两种命令:$var = expr
形式的赋值和$var = $array[$index]
形式的命令 -当然还有其他命令,但这足以解释我的问题。
我创建了一个类型 Command
来表示这一点,以及相应的解析器,其中分配的 expr
由 Parsec 的 buildExpressionParser
处理。
现在,问题来了。首先是解析代码:
main = case parse p "" "$c = $a[$b]" of
Left err -> putStrLn . show $ err
Right r -> putStrLn . show $ r
where p = (try assignment <|> command) <* eof -- (1)
整个代码(50行)粘贴在这里:链接(如果你已经解析了,应该编译安装)
问题是,解析失败,因为赋值
没有成功解析,即使之前有一个try
。反转解析顺序(尝试命令 <|> 赋值
)可以解决问题,但在我的情况下是不可能的。
当然,我尝试进一步定位问题,在我看来,问题出在表达式解析器(由 buildExpressionParser
构建),因为如果我说 expr = failed ""< 则解析会成功。 /代码>。然而,我在秒差距来源中找不到任何可以解释这种行为的内容。
I'm currently using the Text.Parsec.Expr module to parse a subset of a scripting language.
Basically, there are two kinds of commands in this language: Assignment of the form $var = expr
and a Command of the form $var = $array[$index]
- there are of course other commands, but this suffices to explain my problem.
I've created a type Command
, to represent this, along with corresponding parsers, where expr
for the assignment is handled by Parsec's buildExpressionParser
.
Now, the problem. First the parsing code:
main = case parse p "" "$c = $a[$b]" of
Left err -> putStrLn . show $ err
Right r -> putStrLn . show $ r
where p = (try assignment <|> command) <* eof -- (1)
The whole code (50 lines) is pasted here: Link (should compile if you've parsec installed)
The problem is, that parsing fails, since assignment
doesn't successfully parse, even though there is a try
before. Reversing the parsing order (try command <|> assignment
) solves the problem, but is not possible in my case.
Of course I tried to locate the problem further and it appears to me, that the problem is the expression parser (build by buildExpressionParser
), since parsing succeeds if I say expr = fail ""
. However I can't find anything in the Parsec sources that would explain this behaviour.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
您的解析器失败,因为事实上
assigment
does 在这里成功消耗$c = $a
(尝试使用普通的where p = assignment< /代码>)。那么应该有
eof
(或来自assigment
的expr
的其余部分),因此会出现错误。当“赋值”的参数只是一个var
时(例如$c = $a
),“命令”的开头似乎与“赋值”相同代码>)。不知道为什么你不能颠倒
命令
和赋值
,但使这个特定示例工作的另一种方法是:You parser fails because in fact
assigment
does succeeds here consuming$c = $a
(try it with plainwhere p = assignment
). Then there is supposed to beeof
(or the rest ofexpr
fromassigment
) hence the error. It seems that the beggining of your 'command' is identical to your 'assignment' in the case when 'assignment''s argument is just avar
(like$c = $a
).Not sure why you can't reverse
command
andassignment
but another way to make this particular example work would be: