I am using a C lexer that is Flex-generated, and a C++ parser that is Bison-generated. I have modified the parser to acccept only string input.
我正在使用Flex生成的C词法分析器和Bison生成的C ++解析器。我修改了解析器只接受字符串输入。
I am calling the parser function yyparse()
in a loop, and reading line by line of user input. I stop the loop if the input is "quit".
我在循环中调用解析器函数yyparse(),并逐行读取用户输入。如果输入“退出”,我会停止循环。
The problem I am facing is that when input doesn't match any rule, then the parser stops abruptly, and at next iteration starts off at same state, expecting the rule which was stopped (due to syntax error) to complete.
我面临的问题是,当输入与任何规则都不匹配时,解析器会突然停止,并且在下一次迭代开始时处于相同状态,期望停止的规则(由于语法错误)完成。
It works fine if the input is valid and matches a parser rule.
如果输入有效并且与解析器规则匹配,则它可以正常工作。
On syntax error I have redefined the yyerror()
function, that displays a simple error message.
在语法错误上,我重新定义了yyerror()函数,它显示了一个简单的错误消息。
How do I clear the state of the parser when the input doesn't match any parser rule, so that at next iteration the parser starts afresh?
当输入与任何解析器规则不匹配时,如何清除解析器的状态,以便在下一次迭代时解析器重新启动?
2 个解决方案
#1
2
According to my Lex & Yacc book there is a function yyrestart(file) .
根据我的Lex&Yacc书,有一个函数yyrestart(文件)。
Else (and I quote a paragraph of the book:
否则(我引用了本书的一个段落:
This means that you cannot restart a lexer just by calling yylex(). You have to reset it into the default state using BEGIN INITIAL, discard any input text buffered up by unput(), and otherwise arrange so that the next call to input() will start reading the new input.
这意味着只需调用yylex()就无法重新启动词法分析器。您必须使用BEGIN INITIAL将其重置为默认状态,丢弃由unput()缓冲的任何输入文本,否则进行排列,以便下一次对input()的调用将开始读取新输入。
#2
0
Interesting question - I have a parser that can be compiled with Bison, Byacc, MKS Yacc or Unix Yacc, and I don't do anything special to deal with resetting the grammar whether it fails or succeeds. I don't use a Flex or Lex tokenizer; that is hand-coded, but it works strictly off strings. So, I have to agree with Gamecat; the most likely cause of the trouble is the lexical analyzer, rather than the parser proper.
有趣的问题 - 我有一个可以用Bison,Byacc,MKS Yacc或Unix Yacc编译的解析器,并且我没有做任何特别的事情来处理重置语法,无论它是失败还是成功。我不使用Flex或Lex标记器;这是手工编码的,但它严格地用于字符串。所以,我必须同意Gamecat;造成问题的最可能原因是词法分析器,而不是解析器。
(If you want to obtain my code, you can download SQLCMD from the IIUG (International Informix User Group) web site. Although the full product requires Informix ESQL/C, the grammar can, in principle, be converted into a standalone test program. Sadly, however, it appears I've not run that test for a while - there are some issues with the test compilation. Some structure element names changed in April 2006, plus there are linkage issues. I will need to re-reorganize the code so that the grammar can be tested standalone again.)
(如果要获取我的代码,可以从IIUG(国际Informix用户组)网站下载SQLCMD。虽然完整产品需要Informix ESQL / C,但语法原则上可以转换为独立的测试程序。然而,遗憾的是,我似乎暂时没有运行该测试 - 测试编译存在一些问题。2006年4月,一些结构元素名称发生了变化,还有链接问题。我需要重新组织代码这样语法可以再次独立测试。)
#1
2
According to my Lex & Yacc book there is a function yyrestart(file) .
根据我的Lex&Yacc书,有一个函数yyrestart(文件)。
Else (and I quote a paragraph of the book:
否则(我引用了本书的一个段落:
This means that you cannot restart a lexer just by calling yylex(). You have to reset it into the default state using BEGIN INITIAL, discard any input text buffered up by unput(), and otherwise arrange so that the next call to input() will start reading the new input.
这意味着只需调用yylex()就无法重新启动词法分析器。您必须使用BEGIN INITIAL将其重置为默认状态,丢弃由unput()缓冲的任何输入文本,否则进行排列,以便下一次对input()的调用将开始读取新输入。
#2
0
Interesting question - I have a parser that can be compiled with Bison, Byacc, MKS Yacc or Unix Yacc, and I don't do anything special to deal with resetting the grammar whether it fails or succeeds. I don't use a Flex or Lex tokenizer; that is hand-coded, but it works strictly off strings. So, I have to agree with Gamecat; the most likely cause of the trouble is the lexical analyzer, rather than the parser proper.
有趣的问题 - 我有一个可以用Bison,Byacc,MKS Yacc或Unix Yacc编译的解析器,并且我没有做任何特别的事情来处理重置语法,无论它是失败还是成功。我不使用Flex或Lex标记器;这是手工编码的,但它严格地用于字符串。所以,我必须同意Gamecat;造成问题的最可能原因是词法分析器,而不是解析器。
(If you want to obtain my code, you can download SQLCMD from the IIUG (International Informix User Group) web site. Although the full product requires Informix ESQL/C, the grammar can, in principle, be converted into a standalone test program. Sadly, however, it appears I've not run that test for a while - there are some issues with the test compilation. Some structure element names changed in April 2006, plus there are linkage issues. I will need to re-reorganize the code so that the grammar can be tested standalone again.)
(如果要获取我的代码,可以从IIUG(国际Informix用户组)网站下载SQLCMD。虽然完整产品需要Informix ESQL / C,但语法原则上可以转换为独立的测试程序。然而,遗憾的是,我似乎暂时没有运行该测试 - 测试编译存在一些问题。2006年4月,一些结构元素名称发生了变化,还有链接问题。我需要重新组织代码这样语法可以再次独立测试。)