Parsing 具有epsilon乘积的LR(1)解析表

Parsing 具有epsilon乘积的LR(1)解析表,parsing,compiler-theory,lr1,Parsing,Compiler Theory,Lr1,我在为LR(1)解析器构建包含epsilon产品的语法的项集时遇到了问题。例如,给定以下语法(其中eps代表ε) State0将是 S' -> .S, $ S -> .a S U, $ 从State0使用“a”移动将产生以下状态,我们称之为State2 S -> a .S U, $ S -> .a S U, $/??? 为了对State2的第二项进行前瞻,我需要计算第一项(U$)。我知道第一个(U)={b',eps}。我的第一个问题是:State2第二项的首字母是$和

我在为LR(1)解析器构建包含epsilon产品的语法的项集时遇到了问题。例如,给定以下语法(其中eps代表ε)

State0将是

S' -> .S, $
S -> .a S U, $
从State0使用“a”移动将产生以下状态,我们称之为State2

S -> a .S U, $
S -> .a S U, $/???
为了对State2的第二项进行前瞻,我需要计算第一项(U$)。我知道第一个(U)={b',eps}。我的第一个问题是:State2第二项的首字母是$和'b'?因为U可以是eps,我的大脑告诉我,我也可以用美元作为前瞻,而不仅仅是b。如果第一个(U)就是{'b'},那么它就是'b'。对吗

第二个问题:在某个时刻,我会有一个如下的状态

S -> a S .U, $
U -> .b, $
U -> .eps, $
我在这里干什么?我是否需要使用eps进行移动,并使用项目<代码>U->eps.,$进行设置?如果我有另一个终端作为lookahead,即
X->.eps,a/$
,该怎么办?若我移动,最终得到一组形式为<代码>X->eps.,$,我会减少吗

还有更多:我是否需要在解析表中插入eps作为符号

谢谢

  • FIRST(U$)
    表示“在
    U$
    的派生中可能是第一个的符号集”。显然,如果
    U
    可以派生空字符串,
    $
    必须是此集合的一部分。输入结束标记
    $
    确保我们不必担心
    第一个
    集中的ε。(如果我们使用LR(k)而不是LR(1),我们将使用
    k
    结束标记,以便
    FIRSTk
    中的所有字符串都具有长度
    k

  • U关联的项→ (或使用
    U→ ε
    如果您坚持)是
    U→ • 。换句话说,它是可还原的,并且应该在匹配前瞻时触发一个reduce操作

  • ε不是一个符号;我们(有时)只使用它使空字符串可见。但是空字符串是空的


  • 你用什么作为教科书?让我惊讶的是,没有可以为空的非终端的例子。龙之书。我真的不知道我是否遗漏了一些部分,但我没有读到如何具体处理这种情况……是的。我翻出了龙之书的副本,确实没有一个LR自动机的工作示例nε-产生。尽管如此,本书清楚地表明ε代表符号的空序列,而不是特殊符号。(事实上,本书始终使用希腊字母表示符号序列,使用罗马字母表示单个符号,这已成为一种标准惯例。)……此外,其第一(α)的定义实际上是,“如果α可以派生空集,则α加ε派生中可能的第一个字符集,这意味着它是
    ∑的子集∪ ε
    。但是在第一个(β$)的情况下,显然Β$不能派生空序列,因此第一个集合必须是∑的子集。
    S -> a S .U, $
    U -> .b, $
    U -> .eps, $