scala> :paste
// Entering paste mode (ctrl-D to finish)
trait MyOrdering {
type E
def compare(a: E, b: E): Int
}
object MyOrdering {
implicit val intOrdering: MyOrdering { type E = Int } = new MyOrdering {
type E = Int
def compare(a: Int, b: Int): Int = a - b
}
implicit val stringOrdering: MyOrdering { type E = String } = new MyOrdering {
type E = String
def compare(a: String, b: String): Int = a compareTo b
}
}
trait MyList { self =>
type E
def head: E
def last: E
def max(implicit ord: MyOrdering { type E = self.E }): E = {
if (ord.compare(head, last) > 0) head else last
}
}
class IntList(val head: Int, val last: Int) extends MyList {
type E = Int
}
class StringList(val head: String, val last: String) extends MyList {
type E = String
}
val i = new IntList(10, 20)
val s = new StringList("bb", "aa")
// Exiting paste mode, now interpreting.
defined trait MyOrdering
defined module MyOrdering
defined trait MyList
defined class IntList
defined class StringList
i: IntList = IntList@33c405d5
s: StringList = StringList@49530de7
scala> i.max
res0: i.E = 20
scala> s.max
res1: s.E = bb
scala>
ファッ!?
scala> class LongList(val head: Long, val last: Long) extends MyList {
| type E = Long
| }
defined class LongList
scala> val l = new LongList(20L, 10L)
l: LongList = LongList@6e9c814
scala> l.max
<console>:12: error: could not find implicit value for parameter ord: MyOrdering{type E = l.E}
l.max
^
ウゴイタァァァ!!!!