Test code:


class Prefixer(val prefix: String){
  def addPrefix(s: String)(p: Prefixer) = p.prefix + s
}

Consumer code:


val myImplicitPrefixer = new Prefixer("***")
println(myImplicitPrefixer.addPrefix("abc")(myImplicitPrefixer))  // returns "***abc"

The implementation of Prefixer is combined to Java Byte code as below.

The argument list in Scala is converted into flat format (s: String)(p: Prefixer) as below:

/wp-content/uploads/2016/01/clipboard1_867630.png

/wp-content/uploads/2016/01/clipboard2_867631.png

/wp-content/uploads/2016/01/clipboard3_867635.png


The following two styles are actually equal:


def addPrefix(s: String, p: Prefixer) = p.prefix + s
def addPrefix(s: String) (p: Prefixer) = p.prefix + s

Now let’s make a little bit modification:

def addPrefix(s: String)(implicit p: Prefixer) = p.prefix + s

And consumer code:

/wp-content/uploads/2016/01/clipboard4_867636.png

Still ***abc is printed out. What’s the magic here?

When we debug into line 26, although in our application code, we only pass “abc” as parameter for method addPrefix.

The parameter p is filled with the reference myImplicitPrefixer marked with keyword implicit in line 25:

/wp-content/uploads/2016/01/clipboard5_867612.png

p actually points to the same reference of this:

/wp-content/uploads/2016/01/clipboard6_867613.png

This is the compiled byte code for method addPrefix, the implicit parameter p is already in the method’s signature.

/wp-content/uploads/2016/01/clipboard7_867641.png

And in the consumer code, the reference of Prefixer is automatically passed into addPrefix method:

/wp-content/uploads/2016/01/clipboard8_867642.png

One more point, the variable defined in class definition parameter will automatically become member of this class:

/wp-content/uploads/2016/01/clipboard9_867643.png

/wp-content/uploads/2016/01/clipboard10_867644.png

To report this post you need to login first.

Be the first to leave a comment

You must be Logged on to comment or reply to a post.

Leave a Reply