Scala:如何实例化继承当前上下文的解释器? [英] Scala: How to instantiate an interpreter that inherits the current context?

查看:65
本文介绍了Scala:如何实例化继承当前上下文的解释器?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Scala代码中,我想创建一个解释器,该解释器将评估一些Scala代码的字符串,例如,使用ScriptEngine.但是我想将当前变量和类型定义传递给它,以便字符串中的代码可以使用它们,就像新解释器是从当前解释器派生的一样.

In a Scala code, I'd like to create an interpreter that will evaluate some strings which are Scala code, e.g., using ScriptEngine. But I'd like to pass the current variable and type definitions to it so that the code in the strings can use them, as if the new interpreter is forked from the current interpreter.

使用ScriptEngine,我可以使用"put"方法将绑定放入其中,但这对于每个变量都必须是明确的.而且,无法传递类定义或方法等.

With ScriptEngine I could use use the "put" method to put bindings into it, but this needs to be explicit and for each variable. And, there's no way to pass a class definition, or a method etc.

那有办法吗,还是我误会了什么?

Is there a way then, or am I misunderstanding something?

目的是让动态代码使用准备好的数据和方法

The purpose is to let dynamic code to use prepared data and methods

这是我现在可以做的:

import javax.script._
val e = new ScriptEngineManager().getEngineByName("scala")

engine.put("x", 123) 
engine.eval("val y = x.asInstanceOf[Int] + 100")

这就是我想要做的:

case class X(a: Int, b: Int)
val x = X(1,2)

engine.eval("val x1 = X(x.a + 1, x.b + 1)")    // Use both X and x

推荐答案

您可以尝试

val res = engine.eval(
    """case class X(a: Int, b: Int)
      |val x = X(1,2)
      |val x1 = X(x.a + 1, x.b + 1)""".stripMargin)

还可以使用scala.tools.reflect.ToolBox.

使用导入.

package mypackage

import javax.script._

object App {
  val engine = new ScriptEngineManager().getEngineByName("scala")

  case class X(a: Int, b: Int)
  val x = X(1,2)

  val res = engine.eval("import mypackage.App._; val x1 = X(x.a + 1, x.b + 1)")
}

package mypackage

import scala.reflect.runtime.universe._
import scala.tools.reflect.ToolBox

object App {
  val tb = runtimeMirror(ClassLoader.getSystemClassLoader).mkToolBox()

  case class X(a: Int, b: Int)
  val x = X(1, 2)

  val tree = tb.parse("import mypackage.App._; val x1 = X(x.a + 1, x.b + 1)")
  val res = tb.eval(tree)
}

这篇关于Scala:如何实例化继承当前上下文的解释器?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆