【问题标题】:Instantiate Xbase XExpressions programmatically以编程方式实例化 Xbase XExpressions
【发布时间】:2015-07-08 17:49:42
【问题描述】:

我正在开发一个使用部分 Xbase 语法的 Xtext 项目。在我的代码中,我正在分析 DSL 程序以生成一些 Java 代码。使用XbaseCompiler 将现有的XExpression 转换为Java 代码很容易,但这不是我需要的。相反,我需要生成一个不同的程序。

目前我只是在生成 Java 代码(即构造一个字符串)。我想做的是构造一个新的XExpression,甚至可能使用原来的部分,然后将它编译成Java。

不同的XExpressions 有零参数构造函数,所以我尝试实例化一个,甚至设置一些属性。但是编译器崩溃了,我无法确定它缺少哪些属性。

【问题讨论】:

  • 我不知道这是否是一个好主意,但从你所拥有的上下文中很难说,因为除了编写 jvmmodelinferrer 之外所做的每一件事都应该得到充分考虑,因为它可能并不那么容易。但您可能会寻找 XbaseFactory.eInstance.createXXX,因为通常使用所有 EMF 东西

标签: abstract-syntax-tree dsl xtext xbase


【解决方案1】:

我更愿意将表达式生成为字符串,然后使用 Xtext 解析器为您完成繁重的工作,即让它解析字符串并为您创建相应的 XExpression 对象。你如何正确地做到这一点取决于你所处的环境(OSGI 或独立)。

这是来自 Xtext documentation 的“脚本语言”的独立示例(可以从简单的 main 方法运行):

public class StandaloneParser {

    @Inject
    private IParser parser;

    public StandaloneParser() {
        Injector injector = new ScriptingStandaloneSetup().createInjectorAndDoEMFRegistration();
        injector.injectMembers(this);
    }

    public EObject parse(String input) {
        IParseResult result = parser.parse(new StringReader(input));
        if (result.hasSyntaxErrors()) {
            throw new RuntimeException("Syntax errors");
        }
        return result.getRootASTElement();
    }

}

调用者示例:

public class Main {

    public static void main(String[] args) {
        StandaloneParser parser = new StandaloneParser();
        EObject result = parser.parse("val answer = 7 * 6;");
        System.out.println(result);
    }

}

如果您尝试以编程方式创建这样的表达式,您将遇到困难。它可能看起来像这样(Xtend 代码):

val factory = XbaseFactory.eINSTANCE
val expression = factory.createXVariableDeclaration => [
    name = "answer"
    right = factory.createXBinaryOperation => [
        leftOperand = factory.createXNumberLiteral => [
            value = "7"
        ]
        feature = // TODO retrieve the JvmOperation: org.eclipse.xtext.xbase.lib.IntegerExtensions.operator_multiply(int,int)
        rightOperand = factory.createXNumberLiteral => [
            value = "6"
        ]
    ]
]

【讨论】:

  • 感谢您的回答!假设我正在检查访问在其他地方声明的变量的 XBlockExpression。如何告诉解析器对新表达式使用相同的上下文(即范围),以便我可以访问相同的变量?
  • 这在很大程度上取决于您的具体模型/语法。以脚本语言为例,您可以在整个模型上执行 EcoreUtil.copyAll(...)(或修改现有的),删除一些表达式并在您想要的位置放入您自己的表达式。如果这没有为您提供足够的信息,请提交一个新问题,并提供有关您的用例的更多详细信息(请注意,我要到星期二才能有空)。
  • 谢谢,我去看看。
  • 我决定坚持手工生成 Java 代码。
猜你喜欢
  • 2013-08-11
  • 2020-12-29
  • 2011-02-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-03-12
  • 1970-01-01
相关资源
最近更新 更多