ANTLR 语法 - 解析标签和指令

发布于 2025-01-05 16:39:20 字数 925 浏览 4 评论 0原文

我正在编写一个使用指令列表代码的解释器。当我尝试编写带标签的指令语法时遇到一些问题。

我想解析这个代码块:

LD 4
ST A
LD A
EQ 4
ST _AUX_1
(* IF *)
LDN _AUX_1
JMPC _label_2 
(* THEN *)
LD B
EQ 3
ST _AUX_2
_label_2: (* ELSE *)
_label_1: (* END IF*)
LD TRUE

正如你所看到的,这些标签位于一行中,没有指令,但我必须解析的语言允许“标签+指令”在一行中。因此,存在三种不同类型的指令和标签组合:

  1. 指令
  2. 标签:
  3. 标签: 指令

我可以解析 1 和 2,但我无法解析所有不同的组合。

这是我的 ANTLR 语法的摘录:

program_il : instruction* ;

instruction 
        : ID':' // label
        | ID_INST operand
        ;

operando
    : ID
    | CTE_INT
    | CTE_BOOL
    ;

我试图将语法更改为:

instruction : (ID':')? instruction? ;

但我遇到了下一个错误:

As a result, alternative(s) 2 were disabled for that input
[14:43:49] error(201): Analizador.g:131:29: The following alternatives can never be matched: 2

有人可以帮我解决这个问题吗? 先感谢您。

I'm writting an interpreter which uses an Instruction List code. I'm having some problems when I try to write the grammar for instructions with labels.

I'd like to parser this code block:

LD 4
ST A
LD A
EQ 4
ST _AUX_1
(* IF *)
LDN _AUX_1
JMPC _label_2 
(* THEN *)
LD B
EQ 3
ST _AUX_2
_label_2: (* ELSE *)
_label_1: (* END IF*)
LD TRUE

As you can see those labels are in a single line without instructions, but the language I'have to parser allows "label + instruction" in a line. So, there are three differents kinds of combinations of instruction and label:

  1. Instruction
  2. Label:
  3. Label: Instruction

I can parse 1 and 2, but I'm not able to parse all of the different combinations.

This is an extract of my ANTLR grammar:

program_il : instruction* ;

instruction 
        : ID':' // label
        | ID_INST operand
        ;

operando
    : ID
    | CTE_INT
    | CTE_BOOL
    ;

I tried to change the grammar to:

instruction : (ID':')? instruction? ;

But I've got next error:

As a result, alternative(s) 2 were disabled for that input
[14:43:49] error(201): Analizador.g:131:29: The following alternatives can never be matched: 2

Could someone help me with this problem?
Thank you in advance.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

墨洒年华 2025-01-12 16:39:20

因为您现在接受Label:Instruction,所以语法不明确。解析器无法区分:

lbl:
LD 4

lbl: LD 4

换句话说,您需要让您的指令由某种分隔符分隔。换行符可以实现这一点,如以下演示所示:

grammar T;

program_il
 : NL* instruction (NL+ instruction)* NL* EOF
 ;

instruction 
 : ID ':' (ID_INST operand)?
 | ID_INST operand
 ;

operand
 : ID
 | CTE_INT
 | CTE_BOOL
 ;

CTE_BOOL
 : 'TRUE'
 | 'FALSE'
 ;

ID_INST
 : 'LD'
 | 'ST'
 | 'EQ'
 | 'LDN'
 | 'JMPC'
 ;

ID
 : ('_' | 'a'..'z' | 'A'..'Z') ('_' | 'a'..'z' | 'A'..'Z' | '0'..'9')*
 ;

CTE_INT
 : ('0'..'9')+
 ;

NL
 : '\r'? '\n'
 | '\r'
 ;

COMMENT
 : '(*' .* '*)' {skip();}
 ;

SPACE
 : (' ' | '\t')+ {skip();}
 ;

现在解析输入:

(* IF *)
JMPC _label_2 
(* THEN *)
LD B
ST _AUX_2
_label_2: LDN _AUX_1 (* ELSE *)
_label_1: (* END IF*)
LD TRUE

将生成以下树:

Because you now accept Label: Instruction, the grammar is ambiguous. The parser cannot make a distinction between:

lbl:
LD 4

and

lbl: LD 4

In other words, you need to let your instructions be separated by some sort of delimiter. A line break would do the trick as the following demo demonstrates:

grammar T;

program_il
 : NL* instruction (NL+ instruction)* NL* EOF
 ;

instruction 
 : ID ':' (ID_INST operand)?
 | ID_INST operand
 ;

operand
 : ID
 | CTE_INT
 | CTE_BOOL
 ;

CTE_BOOL
 : 'TRUE'
 | 'FALSE'
 ;

ID_INST
 : 'LD'
 | 'ST'
 | 'EQ'
 | 'LDN'
 | 'JMPC'
 ;

ID
 : ('_' | 'a'..'z' | 'A'..'Z') ('_' | 'a'..'z' | 'A'..'Z' | '0'..'9')*
 ;

CTE_INT
 : ('0'..'9')+
 ;

NL
 : '\r'? '\n'
 | '\r'
 ;

COMMENT
 : '(*' .* '*)' {skip();}
 ;

SPACE
 : (' ' | '\t')+ {skip();}
 ;

Now parsing the input:

(* IF *)
JMPC _label_2 
(* THEN *)
LD B
ST _AUX_2
_label_2: LDN _AUX_1 (* ELSE *)
_label_1: (* END IF*)
LD TRUE

will result in the following tree:

enter image description here

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文