Xtext-Python Like DSL 带有合成令牌

问题描述

我正在处理我的 dsl 项目。但是当我想让它像 python(Whitespace-Aware Languages) 一样工作时,它给了我错误“不匹配的输入 '\t' 期待 RULE_BEGIN”。终止规则 BEGIN 是什么意思?为什么下面的例子不能工作? 这是我的语法:

grammar org.pythonDSL.PythonDSL

hidden(WS)

generate pythonDSL "http://www.pythonDSL.org/PythonDSL"

import "http://www.eclipse.org/emf/2002/Ecore" as ecore

PythonDSL:
    (elements+=AbstractElement)*;
 
AbstractElement:
    type=(Stmt|Config);
 
Qualifiedname:
    ID ('.' ID)*;
    
Comment:
    name=(ML_COMMENT|SL_COMMENT);

Import:
    'import' importednamespace=QualifiednameWithWildcard;

Config:
    {Config} 'config' configs=Dictionary;

keyvalue:
    name=QualifiedValue ':' value=QualifiedValue;

QualifiednameWithWildcard:
    Qualifiedname '.*'?;

Qualifiedindex:
INT|STRING;

Dictionary:
    {Dictionary} '{' (elements+=keyvalue)+ '}';

Set:
    {Set} '{' (elements+=QualifiedValue)* '}';

List:
    {List} '[' (elements+=QualifiedValue)* ']';

QualifiedValue:
STRING|'True'|'False'|INT;

VarDec:
name=ID('['index=Qualifiedindex']')? '=' value=QualifiedValue;

Stmt:
 type=(Exp|Import) NEXT_LINE | type=If | type=Comment;

If:
    'if' (not='not')? condition=Exp ':' NEXT_LINE?
     (BEGIN ( ifStmts+=Stmt)* END)
    (=> elseIfClause+=ElseIf)*
    (=> elseClause=Else)?;

ElseIf:
    'elif'  condition=Exp ':' NEXT_LINE?
     (BEGIN ( elseIfStmts+=Stmt)* END);

Else:
    {Else} 'else' NEXT_LINE? (BEGIN ( elseStmts+=Stmt)* END);

Exp:
    left=Equal;

Ret:
    'return' name=ID;

Var:
    name=ID;


Val:
    name=QualifiedValue | type=(Dictionary|List|Set);

Dot returns Exp:
    left=Array ({Dot.left=current} op='.'right=Array)*
;

Array returns Exp:
    left=Primary ({Array.left=current} op='['right=Primary']')*
;

Primary returns Exp:
   op='(' left=Equal ')' |left=Var|left=Val|left=FuncCall;

ArgList:
    {ArgList} (args+=Equal)? (',' args+=Equal)*;

FuncCall:
    name=Var (op='(' right=ArgList ')');

Equal returns Exp:
    left=AddAndSub ({Euqal.left=current} op='=' right=AddAndSub)*;

AddAndSub returns Exp:
    left=MulAndDiv ({AddAndSub.left=current} op=('+'|'-') right=MulAndDiv)*;

MulAndDiv returns Exp:
    left=Dot ({MulAndDiv.left=current} op=('*'|'/') right=Dot)*;

terminal BEGIN: 'synthetic:BEGIN';  // increase indentation
terminal END: 'synthetic:END';      // decrease indentation

terminal ID:
    '^'?('a'..'z'|'A'..'Z'|'_')('a'..'z'|'A'..'Z'|'_'|'0'..'9')*;
 
terminal INT returns ecore::EInt:
    ('0'..'9')+;
 
terminal STRING:
    '"' ( '\\'('b'|'t'|'n'|'f'|'r'|'u'|'"'|"'"|'\\') | !('\\'|'"') )* '"' |
    "'" ( '\\'('b'|'t'|'n'|'f'|'r'|'u'|'"'|"'"|'\\') | !('\\'|"'") )* "'";
 
terminal ML_COMMENT:
    "'''" -> "'''";
 
terminal SL_COMMENT:
    '#' !('\n'|'\r')* ('\r'? '\n')?;
 
terminal WS:
    (' ')+;
/*    
terminal TAB:
    ('\t')+;
    */
terminal NEXT_LINE:
    ('\n'|'\r')+;

terminal ANY_OTHER:
    .;

这是我的例子:

a = b
if a.b:
    el.click()
elif c:
    '''les '''
    e.go()
elif m:
    if lake:
        pik()
else:
    e1.click()

主要问题是if-else子句,这个子句需要检测缩进。 我需要 NEXT_LINE 规则来确保一个 stmt 只有一行。 在简单的语法中,BEGIN 和 END 规则可以工作。但是当我添加 NEXT_LINE 规则时,它失败了。

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...