编写没有语法文件的自定义Xtext/ANTLR词法分析器

Ada*_*deg 9 antlr lexer xtext

我正在为CoffeeScript编写一个Eclipse/Xtext插件,我意识到我可能需要手工编写一个lexer.CoffeeScript解析器还使用手写的词法分析器来处理语法中的缩进和其他技巧.

Xtext生成一个扩展的类,org.eclipse.xtext.parser.antlr.Lexer然后扩展org.antlr.runtime.Lexer.所以我想我会扩展它.我可以看到两种方法

  • 覆盖mTokens().这是由生成的代码完成的,改变了内部状态.
  • 覆盖nextToken()这似乎是一种自然的方法,但随后我将不得不跟踪内部状态.

我找不到任何例子如何在没有语法文件的情况下为ANTLR写一个简单的词法分析器.所以最简单的答案就是指向一个指针.

Xtext的回答:具有重要/语义空白的语言的语法指的是通过改变底层输入流中的标记来处理缩进问题的todotext.我不想这样做,因为很难处理coffeescript语法的其他技巧.

更新:

在此期间我意识到我的问题部分是特定于Xtext的.

Ada*_*deg 8

这就是我做的 - 而且它有效.

public class MyLexer extends myprj.parser.antlr.internal.InternalMylangLexer {
  private SomeExternalLexer externalLexer;

  public Lexer(CharStream in) {
    super(in);
    externalLexer = new SomeExternalLexer(in);
  }

  @Override
  public Token nextToken() {
    Token token = null;
    ExternalToken extToken = null;
    try {
      extToken = externalLexer.nextToken();
      if (extToken == null) {
        token = CommonToken.INVALID_TOKEN;
      }
      else {
        token = mapExternalToken(extToken);
      }
    }
    catch (Exception e) {
      token = CommonToken.INVALID_TOKEN;
    }
    return token;
  }

  protected Token mapExternalToken(ExternalToken extToken) {
    // ...
  }
}
Run Code Online (Sandbox Code Playgroud)

然后我有一个稍微定制的解析器包含:

public class BetterParser extends MylangParser {
  @Override
  protected TokenSource createLexer(CharStream stream) {
    MyLexer lexer = new MyLexer(stream);
    return lexer;
  }
}
Run Code Online (Sandbox Code Playgroud)

我还必须改变我的MylangRuntimeModule.java方法来包含这个方法

@Override
public Class<? extends org.eclipse.xtext.parser.IParser> bindIParser() {
     return myprj.parser.BetterParser.class ;
}
Run Code Online (Sandbox Code Playgroud)

就是这样.


Mat*_*iez 6

另一种方法(无需创建自定义解析器)是通过扩展Xtext的词法分析器(org.eclipse.xtext.parser.antlr.Lexer)来创建自定义词法分析器,如下所示:

public class CustomSTLexer extends Lexer {

    @Override
    public void mTokens() {
      // implement lexer here
    }
}
Run Code Online (Sandbox Code Playgroud)

然后在模块中绑定它:

@Override
public void configureRuntimeLexer(Binder binder) {
    binder.bind(Lexer.class)
                .annotatedWith(Names.named(LexerBindings.RUNTIME))
                .to(CustomSTLexer.class);
}
Run Code Online (Sandbox Code Playgroud)

如果你想看一个完整的例子,我已经为StringTemplate的一个名为hastee的基于Xtext的编辑器实现了一个自定义词法分析器.