开始使用C ++中的语法分析器的代码结构

时间:2015-10-11 22:58:06

标签: c++ string parsing grammar

我现在正在为学校做作业,专注于为简单的指令集构建一个标记器和解析器。该指令集使用我们必须输出给用户的EBNF语法。举个简单的例子,假设这个指令集代码如下所示:

set 0, 2 * (4 + 20)
halt

EBNF语法是这样给出的:

<Program>    -> <Statement> { <Statement> }
<Statement>  -> <Set> | 'halt'
<Set>        -> set ('write'|<Expr>), ('read'|<Expr>)
<Expr>       -> <Term> {(+|-) <Term>}
<Term>       -> <Factor> {(*|/|%) <Factor>}
<Factor>     -> <Number> | 'D['<Expr>']' | '('<Expr>')'
<Number>     -> 0 | (1...9){0...9}

在这种情况下,<...>是我输出给用户的内容,{...}表示选择0或更多,(...)表示选择1或更多,&#39; ...& #39;是一个字符串文字。

因此,在这种情况下,运行程序时,正确的输出应如下所示:

Program          
Statement        
Set              // set
Expr             // 0
Term             // 0 is a term
Factor           // 0 is a factor
Number           // 0 is finally a number
Expr             // go to the next string, "2*(4+2)"
Term             // start with the number 2
Factor           // 2 is a factor
Number           // 2 is a number
Factor           // after 2, we have a * so after that is a factor
Expr             // the factor leads to a (...) which leads to an expr
Term             // the expr leads to a term 4
Factor           // 4 is a factor
Number           // 4 is returned as a number
Term             // we have a + so the next string (20) is a term
Factor           // 20 is a factor
Number           // return 20 as a number
Statement        // halt is a statement, end

我已经构建了赋值的tokenizer部分,因此运行上面的指令集会产生一个std::vector<std::string>,看起来像这样(每个新字符串用新行分隔):

set
0
2*(4+20)
halt

现在解析器就是我被卡住的地方。我首先将每个字符串推入std::queue,检查字符串,解析它,然后从队列中弹出它。我已经拥有它,以便set语句推送字符串&#34; Set&#34;在另一个std::vector<std::string>中,我可以稍后打印出来。

我还有一个函数parse_expression(std::string& str)来解析我的表达式。我遇到的真正麻烦在于如何正确解析2 * (4 + 20)部分。

我的老师告诉我要通过字符串逐个字符,检查它是否是一个数字(我知道该怎么做),或者它是否匹配&#39; +&#39;,&#39; - &#39;,&#39; /&#39;,&#39; *&#39;,&#39;%&#39;角色,或者如果下一个角色是&#39; D&#39;然后我应该解析另一个表达。

我对如何尝试这一点感到困惑。如果我逐个字符,我可以获得第一个数字,直到我点击非数字字符,然后只需Term后跟Factor后跟Number。但是,我怎么能回到那个原始角色并继续前进到下一个角色。几乎就像,我如何回到原来的水平,以便我能够正确地确定是否需要创建另一个Expr,或者我是否应该再做一个术语。

我意识到这是一个长期的,令人困惑的问题,但我会感谢任何正确方向的推动,是否明显是我做错了,或者它是否是解析器实际工作的方式。< / p>

0 个答案:

没有答案