2016-10-26 1 views
1

Leider ist die intuitive Art und Weise,scala - Einfügewert in quasiquote

val world = "Earth" 
val tree = q"""println("Hello $world")""" 

Ergebnisse in

Error:(16, 36) Don't know how to unquote here 
val tree = q"""println("Hello $world")""" 
        ^

weil $ innerhalb quasiquotes eine tree erwartet.

val world = "Earth" 
val tree = q"""println(${c.literal(s"Hello $world")})""" 

funktioniert, ist aber sehr hässlich und ich bekomme eine Intellij Warnung, dass die c.literal veraltet und ich sollte quasiquotes verwenden, statt.

Also ... wie mache ich das?

UPDATE

Als Reaktion auf flavian Kommentar:

import scala.language.experimental.macros 
import scala.reflect.macros._ 

object TestMacros { 

    def doTest() = macro impl 

    def impl(c: blackbox.Context)(): c.Expr[Unit] = { 
    import c.universe._ //access to AST classes 
    /* 
    val world = "Earth" 
    val tree = q"""println(${c.literal(s"Hello $world")})""" 
    */ 

    val world = TermName("Earth") 
    val tree = q"""println("Hello $world")""" 

    tree match { 
     case q"""println("Hello Earth")""" => println("succeeded") 
     case _ => c.abort(c.enclosingPosition, s"huh? was: $tree") 
    } 

    c.Expr(tree) //wrap tree and tag with its type 
    } 
} 

Error:(18, 40) Don't know how to unquote here 
    val tree = q"""println("Hello $world")""" 
           ^

Antwort

5

Sie benötigen, dass ein Compiler primitiv ist ein TermName oder etwas gibt.

Das eigentliche Problem ist, dass Sie Interpolatoren mischen, ohne zu realisieren. Der Interpolator in Hello World ist wirklich ein String-Interpolator, kein Quasi-Quot, der gut darin ist, Bäume zu entfernen, wie Sie vorschlagen.

Dies ist eine Möglichkeit, darüber zu gehen:

import c.universe._ 

val world = TermName("Earth") 
val tree = q"""println("Hello" + ${world.decodedName.toString})""" 
+0

könnten Sie erarbeiten „Interpolator in hallo Welt ist wirklich ein String-Interpolator, kein quasiquote eines“? – User1291

+0

auch, keine der beiden Möglichkeiten, die Sie vorschlagen, arbeiten. In der ersten wird der Compiler beschweren, dass "Welt" ist ihm nicht bekannt, in der zweiten wird er sich beschweren, dass er nicht weiß, wie das zu heben ist. – User1291

+0

Ich habe getestet, bevor Sie antworten, Sie tun etwas und Lee möglicherweise falsch. Welche Version von Scala benutzt du? – flavian