Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

__FUNC__ macro in Scala 2.10

In Scala 2.9.x, I wrote the func function which gives me back the name of the function where func() is executed like the FUNC C preprocessor macro. I understand that in Scala2.10 I should be able to write something more elegant than throwing an exception to do the job.

How can I do it? Thanks in advance for your help.

object TestMyLog extends App {
    val MatchFunc = """(.+)\(.+""".r

def func(i_level: Int): String = {
    val s_rien = "functionNotFound"
    try {
    throw new Exception()
    } catch {
    case unknwn => unknwn.getStackTrace.toList.apply(i_level).toString match {
            case MatchFunc(funcs) => funcs.split('.').toList.last
        case _ => s_rien
    }
    } finally {
    s_rien      
    }
}

def tracedFunction1 = func(1)
def tracedFunction2 = func(1)

println(tracedFunction1)
assert(tracedFunction1=="tracedFunction1")
println(tracedFunction2)
assert(tracedFunction2=="tracedFunction2")
}
like image 225
Eric Mariacher Avatar asked Jan 01 '13 22:01

Eric Mariacher


People also ask

What is the use of macro in Scala?

With a macro, we can treat programs as values, which allows us to analyze and generate them at compile time. A Scala expression with type T is represented by an instance of the type scala.quoted.Expr [T].

How do I use the macro Paradise plugin with Scala?

Follow the instructions at the “Macro Paradise” page to download and use our compiler plugin if using those older Scala versions. Note that the macro paradise plugin is needed both to compile and to expand macro annotations, which means that your users will have to also add macro paradise to their builds in order to use your macro annotations.

How do you debug macros in Scala IDE?

Both in Scala IDE and in Intellij IDEA macros are known to work fine, given they are moved to a separate project. Debugging macros (i.e. the logic that drives macro expansion) is fairly straightforward. Since macros are expanded within the compiler, all that you need is to run the compiler under a debugger.

How to work with more complex expressions in Scala 3?

In order to work with more complex expressions, Scala 3 offers different metaprogramming facilities ranging from each increasing in complexity and potentially losing safety guarantees. It is generally recommended to prefer simple APIs over more advanced ones.


1 Answers

import scala.reflect.macros.Context
import scala.language.experimental.macros

def impl(c: Context) = {
  import c.universe._
  c.enclosingMethod match {
    case DefDef(_, name, _, _, _, _) =>
      c.universe.reify(println(c.literal(name.toString).splice))
    case _ => c.abort(c.enclosingPosition, "no enclosing method")
  }
}

scala> def printEnclosingMethod = macro impl
defined term macro printEnclosingMethod: Unit

scala> def foo = printEnclosingMethod
foo: Unit

scala> foo
foo

scala> printEnclosingMethod
<console>:32: error: no enclosing method
              printEnclosingMethod
              ^
like image 188
Eugene Burmako Avatar answered Oct 28 '22 22:10

Eugene Burmako