Scala implicit type conversion and ==
Can anyone enlighten me as to why implicit type conversion does not work with ==
?
Example:
class BitArray(l: Int, v: Long) {
val length = l
var value = v
def ==(that: BitArray) = value == that.value
def ==(integer: Long) = value == integer
def +(that: BitArray) = new BitArray(length,value+that.value )
def +(integer: Long) = new BitArray(length,value+integer )
//...
}
object BitArray{
implicit def longToBitArray(x : Long) = new BitArray(64,x)
def apply(v: Long) :BitArray = apply(64,v)
}
Now I can do:
scala> BitArray(5) + 5
res13: BitArray = 0000000000000000开发者_C百科0000000000001010
scala> 5 + BitArray(5)
res14: BitArray = 00000000000000000000000000001010
scala> BitArray(5) == 5
res15: Boolean = true
scala> BitArray(5) == 6
res16: Boolean = false
BUT:
scala> 5 == BitArray(5)
<console>:11: warning: comparing values of types Int and BitArray using `==' will
always yield false
5 == BitArray(5)
^
res17: Boolean = false
You are missing a fundamental aspect of Scala, which is how equality works.
Basically, all classes extending AnyRef
implement the following method:
def equals (arg0: Any) : Boolean
And all classes implement the following method:
def == (arg0: Any) : Boolean
Now, you should override not ==
, but equals
. The method ==
will call equals
, but Java code will use equals
, not ==
. This is not the cause of the problem you see, but it is important enough that I think it is worth mentioning.
Now, as to the implicit not working, remember that implicits are only looked for if there is no method that satisfy your code. However, Int
's ==
can be compared with BitArray
, as ==
receives an argument of type Any
. Therefore, Int
's equality method is called, and no implicit is looked for.
To override the ==
operator, you should actually override the equals
method:
override def equals(other: Any): Boolean = other match {
case ba: BitArray => value == ba.value
case _ => false
}
You can't make an instance of your BitArray
equal to a Long
and still obey the equals contract (ie. it won't be symmetric).
Adding to the other answers, remember that the equals function has to be SYMMETRIC, that is (a equals b) == (b equals a)
.
精彩评论