Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sql-server-2005/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Antlr 如何将一个令牌的长度依赖于另一个令牌的值?_Antlr_Binary Data_Antlr4 - Fatal编程技术网

Antlr 如何将一个令牌的长度依赖于另一个令牌的值?

Antlr 如何将一个令牌的长度依赖于另一个令牌的值?,antlr,binary-data,antlr4,Antlr,Binary Data,Antlr4,我想标记一些二进制数据,其中一些部分的长度取决于前一个标记的值。你可以这样想: <length><binary data> 假设length是两个字节的无符号整数,表示二进制数据的长度(以字节为单位) 如何实现与ANTLR 4的这种关联?您可能需要扩展ANTLR的输入流。到目前为止,只有输入流和由char[]备份,这可能不适合您匹配任何类型二进制数据的要求 如您所述,要使lexer上下文敏感,您可以: 匹配一个无符号的数字标记,一旦匹配,就用这个值初始化一个实例变

我想标记一些二进制数据,其中一些部分的长度取决于前一个标记的值。你可以这样想:

<length><binary data>

假设length是两个字节的无符号整数,表示二进制数据的长度(以字节为单位)


如何实现与ANTLR 4的这种关联?

您可能需要扩展ANTLR的输入流。到目前为止,只有输入流和由
char[]
备份,这可能不适合您匹配任何类型二进制数据的要求

如您所述,要使lexer上下文敏感,您可以:

  • 匹配一个
    无符号的
    数字标记,一旦匹配,就用这个值初始化一个实例变量(
    bytesToConsume
  • 设置此
    bytesToConsume
    后,只要此
    bytesToConsume
    大于0,就使用字节/字符
  • 当然,只要初始化了
    bytesToConsume
    ,您就不想匹配
    未签名的
    令牌
    
!!这些检查由
{boolean expression}?
执行

演示:

grammar T;

@lexer::members {

  private int bytesToConsume = -1;         

  boolean binary() {
    if(bytesToConsume < 0) {
      return false;
    }
    bytesToConsume--;
    return true;
  }
}

parse
 : block* EOF
 ;

block
 : UNSIGNED BINARY
 ;

UNSIGNED 
 : {!binary()}? 
   [0-9a-fA-F] [0-9a-fA-F] {bytesToConsume = Integer.parseInt(getText(), 16);}
 ;

BINARY
 : ({binary()}? . )+
 ;
通过执行以下操作进行测试:

*尼克斯 java-jar-antlr-4.0-complete.jar T.g4 javac-cp.:antlr-4.0-complete.jar*.java java-cp.:antlr-4.0-complete.jar Main 窗户 java-jar-antlr-4.0-complete.jar T.g4 javac-cp。;antlr-4.0-complete.jar*.java java-cp。;antlr-4.0-complete.jar Main 您将看到以下内容被打印到控制台(尽管我添加了缩进):

(解析)
(03座aaa)
(BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB
(第01 c区)
)
编辑
也许通过使用ANTLR4,清洁剂是可能的。然而,我对v4还很陌生,我不知道这是否可行,因为一旦消耗了一定数量的字节/字符,就要弹出到默认的词法作用域,而不是二进制模式中的明确结束

谢谢你的答复,请原谅我迟来的答复。我认为这是解决这个问题的方法,有一个计数器用于消耗字节。我也是ANTLR的新手,我想我需要一段时间才能给你的建议提供更合理的反馈。 java -jar antlr-4.0-complete.jar T.g4 javac -cp .:antlr-4.0-complete.jar *.java java -cp .:antlr-4.0-complete.jar Main java -jar antlr-4.0-complete.jar T.g4 javac -cp .;antlr-4.0-complete.jar *.java java -cp .;antlr-4.0-complete.jar Main