gpt4 book ai didi

antlr - ANTLR 3 中 wikitext-to-HTML 的工作示例

转载 作者:行者123 更新时间:2023-12-02 17:53:30 26 4
gpt4 key购买 nike

我正试图在 ANTLR 3 中充实一个 wiki 文本到 HTML 的翻译器,但我一直被卡住。

您知道我可以检查的工作示例吗?我尝试了 MediaWiki ANTLR 语法和 Wiki Creole 语法,但我无法让它们在 ANTLR 3 中生成词法分析器和解析器。

以下是我尝试使用的两种语法的链接:

我无法使用这两个来生成我的 Java Lexer 和 Parser。 (我使用 ANTLR3 作为 Eclipse 插件)。 MediaWiki 需要很长时间来构建,然后在某个时候它会抛出 OutOfMemory 异常。另一个有错误,我不知道如何调试。

编辑:好吧,我有一个非常基本的语法:

grammar wikitext;

options {
//output = AST;
//ASTLabelType = CommonTree;
output = template;
language = Java;
}

document: line (NL line?)*;

line: horizontal_line | list | heading | paragraph;

/* horizontal line */
horizontal_line: HRLINE;

/* lists */
list: unordered_list | ordered_list;

unordered_list: '*'+ content;
ordered_list: '#'+ content;

/* Headings */
heading: heading1 | heading2 | heading3 | heading4 | heading5 | heading6;
heading1: H1 plain H1;
heading2: H2 plain H2;
heading3: H3 plain H3;
heading4: H4 plain H4;
heading5: H5 plain H5;
heading6: H6 plain H6;

/* Paragraph */
paragraph: content;

content: (formatted | link)+;

/* links */
link: external_link | internal_link;

external_link: '[' external_link_uri ('|' external_link_title)? ']';
internal_link: '[[' internal_link_ref ('|' internal_link_title)? ']]' ;

external_link_uri: CHARACTER+;
external_link_title: plain;
internal_link_ref: plain;
internal_link_title: plain;

/* bold & italic */
formatted: bold_italic | bold | italic | plain;

bold_italic: BOLD_ITALIC plain BOLD_ITALIC;
bold: BOLD plain BOLD;
italic: ITALIC plain ITALIC;

/* Plain text */
plain: (CHARACTER | SPACE)+;


/**
* LEXER RULES
* --------------------------------------------------------------------------
*/

HRLINE: '---' '-'+;

H1: '=';
H2: '==';
H3: '===';
H4: '====';
H5: '=====';
H6: '======';

BOLD_ITALIC: '\'\'\'\'\'';
BOLD: '\'\'\'';
ITALIC: '\'\'';

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

CHARACTER : '!' | '"' | '#' | '$' | '%' | '&'
| '*' | '+' | ',' | '-' | '.' | '/'
| ':' | ';' | '?' | '@' | '\\' | '^' | '_' | '`' | '~'
| '0'..'9' | 'A'..'Z' |'a'..'z'
| '\u0080'..'\u7fff'
| '(' | ')'
| '\'' | '<' | '>' | '=' | '[' | ']' | '|'
;

SPACE: ' ' | '\t';

我不清楚如何输出 HTML。我一直在研究 StringTemplate,但我不明白如何构建我的模板。具体来说,哪个模板在语法中的哪个位置。你能帮我举个简短的例子吗?

最佳答案

好的,在你的编辑之后,我有一些建议。

正如我在评论中所说,为这种语言编写语法几乎是不可能的。至少,尝试一次性做到这一点。我看到这种工作的唯一方法是使用多个解析器来执行此操作,其中第一个“解析阶段”将非常“粗略”地解析 wiki 源。例如:table 将被标记为:TABLE : '{|' .* '|}' 然后您将创建另一个解析器来正确解析此表。在一个解析器中执行此操作会导致您的解析器规则 IMO 中出现相当多的歧义。

关于发出 HTML 代码,执行此操作的“正确”方法确实是使用 StringTemplate,但考虑到您对 ANTLR 本身相当陌生,我会保持简单。您可以在解析器类中创建一个 StringBuilder 属性,它会在您解析源文件时收集所有 HTML 代码。您可以通过使用 {} 将代码嵌入到 ANTLR 规则中。

这是一个快速演示:

grammar T;

@parser::members {

// an attribute that is only available in your
// parser (so only in parser rules!)
protected StringBuilder htmlBuilder = new StringBuilder();
}

// Parser rules
parse
: atom+ EOF
;

atom
: header
| Any {htmlBuilder.append($Any.text);} // append the text from 'Any' token
;

header
: H3 h3Content H3 {htmlBuilder.append("<h3>" + $h3Content.text + "</h3>");}
| H2 h2Content H2 {htmlBuilder.append("<h2>" + $h2Content.text + "</h2>");}
| H1 h1Content H1 {htmlBuilder.append("<h1>" + $h1Content.text + "</h1>");}
;

h3Content : ~H3*; // match any token except H3, zero or more times
h2Content : ~H2*; // " H2 "
h1Content : ~H1*; // " H1 "

// Lexer rules
H3 : '===';
H2 : '==';
H1 : '=';

// Fall through rule: if non of the above
// lexer rules matched, this one will.
Any
: .
;

根据该语法,您生成解析器和词法分析器:

java -cp antlr-3.2.jar org.antlr.Tool T.g

然后创建一个小类来测试你的解析器:

import org.antlr.runtime.*;

public class Main {
public static void main(String[] args) throws Exception {

// the source to be parsed
String source =
"= header 1 = \n"+
" \n"+
"some text here \n"+
" \n"+
"=== header level 3 === \n"+
" \n"+
"and some more text ";

ANTLRStringStream in = new ANTLRStringStream(source);
TLexer lexer = new TLexer(in);
CommonTokenStream tokens = new CommonTokenStream(lexer);
TParser parser = new TParser(tokens);

// invoke the start-rule in your parser
parser.parse();

// print the contents of your parser's StringBuilder
System.out.println(parser.htmlBuilder);
}
}

然后编译所有源文件:

javac -cp antlr-3.2.jar *.java

最后,运行你的主类

// *nix & MacOS
java -cp .:antlr-3.2.jar Main

// Windows
java -cp .;antlr-3.2.jar Main

这会将以下内容打印到控制台:

<h1> header 1 </h1>             

some text here

<h3> header level 3 </h3>

and some more text

但是,再次声明,如果您可以自由选择不同的语言来解析,我会这样做而忘记解析这个可怕的 Wiki 东西。

无论如何,无论您做什么:祝您好运!

关于antlr - ANTLR 3 中 wikitext-to-HTML 的工作示例,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4810957/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com