这个最简单的jflex代码有什么问题?

时间:2014-04-12 14:52:22

标签: jflex

我正在学习jflex,写了一个最简单的jflex代码,它生成一个单个字符#

import com.intellij.lexer.FlexLexer;
import com.intellij.psi.tree.IElementType;

%%

%class PubspecLexer
%implements FlexLexer
%unicode
%type IElementType
%function advance
%debug

Comment = "#"

%%

{Comment} { System.out.println("Found comment!"); return PubTokenTypes.Comment; }
.                                        { return PubTokenTypes.BadCharacter; }

然后我生成一个PubspecLexer类,并尝试它:

public static void main(String[] args) throws IOException {
    PubspecLexer lexer = new PubspecLexer(new StringReader("#!!!!!"));
    for (int i = 0; i < 3; i++) {
        IElementType token = lexer.advance();
        System.out.println(token);
    }
}

但它打印3 null s:

null
null
null

为什么它既不返回Comment也不返回BadCharacter

1 个答案:

答案 0 :(得分:2)

这不是jflex问题,实际上,这是因为idea-flex改变了原始用法。

当使用jflex编写intellij-idea插件时,我们使用修补的“JFlex.jar”和“idea-flex.skeleton”,稍后将zzRefill方法定义为:

private boolean zzRefill() throws java.io.IOException {
    return true;
}

而不是原创:

private boolean zzRefill() throws java.io.IOException {

  // ... ignore some code 

  /* finally: fill the buffer with new input */
  int numRead = zzReader.read(zzBuffer, zzEndRead,
                                          zzBuffer.length-zzEndRead);
  // ... ignore some code

  // numRead < 0
  return true;
}

请注意代码中有一个zzReader,其中包含我传入的字符串#!!!!!。但是在idea-flex版本中,它从未使用过。

因此,为了使用idea-flex版本,我应该像这样使用它:

public class MyLexer extends FlexAdapter {
    public MyLexer() {
        super(new PubspecLexer((Reader) null));
    }
}

然后:

public static void main(String[] args) {
    String input = "#!!!!!";
    MyLexer lexer = new MyLexer();
    lexer.start(input);
    for (int i = 0; i < 3; i++) {
        System.out.println(lexer.getTokenType());
        lexer.advance();
    }
}

打印哪些:

match: --#--
action [19] { System.out.println("Found comment!"); return PubTokenTypes.Comment(); }
Found comment!
Pub:Comment
match: --!--
action [20] { return PubTokenTypes.BadCharacter(); }
Pub:BadCharacter
match: --!--
action [20] { return PubTokenTypes.BadCharacter(); }
Pub:BadCharacter