Question

Why iWantInt(a) does not compile while iWantInt(b) and - what is more surprising - iWantInt does ?

How can I understand this behaviour ?

Why can I not pass explicitly a to iWantInt when I can pass it implicitly ?

How is iWantA different from iWantInt ? Why does it not work the same way ?

Is this behavior documented/explained somewhere ?

If Scala would accept iWantInt(a) what kind of problems would that cause ? Why is it forbidden ?

class A

class B

object Run extends App {
  implicit val a = new A
  implicit val b = new B
  implicit def A2Int(implicit a:A)=1
  implicit def B2Int(b:B)=2
  def iWantA(implicit a:A)=println("A")
  def iWantInt(implicit i: Int) = println(i)

  iWantInt(b) // prints 2

  iWantInt    // prints 1
//  iWantInt(a) // when uncommented this line does not compile, why ?

  iWantA      // prints A
  iWantA(a)   // prints A
}
Was it helpful?

Solution

Instead of defining an implicit conversion, A2Int acts like a value that has been declared implicit, like implicit val a in the example, the only difference being that an implicit A must be discovered in scope for it to work. This is what allows iWantInt without an explicit parameter to compile - the compiler finds A2Int as the implicit Int, then finds a as the implicit A for A2Int.

For a function to qualify as an implicit conversion it must take a single non-implicit parameter. B2Int takes the single parameter (b: B) and so meets the requirement. This allows iWantInt(b) to compile. A2Int has (implicit a: A) but because this parameter is implicit A2Int does not meet the requirement and so iWantInt(a) does not compile, unless a line like implicit def A2Int2(a:A) = 1 is added. If you run scalac with the -feature flag (which it will suggest at least with 2.11) it will display warnings for B2Int and A2Int2, saying that implicit conversions should be explicitly enabled by making visible scala.language.implicitConversions. It does not show the warning for A2Int, demonstrating that the compiler does not treat it as an implicit conversion.

The Scala Language Reference is the definitive definition for Scala. See Chapter 7, "Implicit Parameters and Views" for the specification of how these particular features behave.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top