45
實例它在斯卡拉2.10我如何生成的字符串類(可能使用工具箱API)後與Scala的反射被實例化?從生成字符串類,並在斯卡拉2.10
實例它在斯卡拉2.10我如何生成的字符串類(可能使用工具箱API)後與Scala的反射被實例化?從生成字符串類,並在斯卡拉2.10
W.r.t彙編工具箱只能運行表達式=返回值,但不能得到的類或文件/字節數組與編譯結果。
但是它仍然可能實現你想要什麼,因爲在斯卡拉它很容易使用隱式值從類型層面去值水平:
編輯。在2.10.0-RC1中,ToolBox
的一些方法已被重命名。 parseExpr
現在只是parse
,runExpr
現在被稱爲eval
。
scala> import scala.reflect.runtime._ // requires scala-reflect.jar
// in REPL it's implicitly added
// to the classpath
// but in your programs
// you need to do this on your own
import scala.reflect.runtime
scala> val cm = universe.runtimeMirror(getClass.getClassLoader)
cm @ 41d0fe80: reflect.runtime.universe.Mirror = JavaMirror with scala.tools.nsc.interpreter.IMain$TranslatingClassLoader...
scala> import scala.tools.reflect.ToolBox // requires scala-compiler.jar
// in REPL it's implicitly added
// to the classpath
// but in your programs
// you need to do this on your own
import scala.tools.reflect.ToolBox
scala> val tb = cm.mkToolBox()
tb: scala.tools.reflect.ToolBox[reflect.runtime.universe.type] = [email protected]
scala> tb.runExpr(tb.parseExpr("class C; scala.reflect.classTag[C].runtimeClass"))
res2: Any = class __wrapper$1$f9d572ca0d884bca9333e251c64e980d$C$1
更新#1。如果您不需要java.lang.Class,只需要實例化編譯後的類,則可以直接在提交到runExpr
的字符串中編寫new C
。
更新#2。也可以讓runExpr
使用從變量名到運行時值的自定義映射。例如:
scala> val build = scala.reflect.runtime.universe.build
build: reflect.runtime.universe.BuildApi = [email protected]
scala> val x = build.setTypeSignature(build.newFreeTerm("x", 2), typeOf[Int])
x: reflect.runtime.universe.FreeTermSymbol = free term x
scala> tb.runExpr(Apply(Select(Ident(x), newTermName("$plus")), List(Literal(Constant(2)))))
res0: Any = 4
在這個例子中我創建具有爲2的值的自由項(該值不必是一個原始的 - 它可以是自定義的對象)以及標識符綁定到它。然後將此值原樣用於由工具箱編譯和運行的代碼。
的例子使用手冊AST組裝,但它是可以編寫解析字符串,發現了綁定標識,查找他們值某種映射函數,然後創建相應的免費條款。雖然在Scala 2.10.0中沒有這樣的功能。
謝謝!一個後續:有沒有辦法讓我用Scala的反射來處理這個返回的'java.lang.Class',或者我只需要堅持原來的Java呢? –
當然。使用' .classSymbol()',其中 ='scala.reflect.runtime.universe.runtimeMirror(.getClassLoader )'。然後你會得到一個Scala反射符號,可以使用Scala反射API進行檢查。 –
爲什麼您使用的''而不是universe.runtimeMirror(getClass.getClassLoader)'reflect.runtime.currentMirror'和'scala.reflect.classTag [C] .runtimeClass',而不是'classOf [C]'?事實證明,我的工作很好。謝謝你的幫助,順便說一句! –