Context Bound,上下文界定,是Scala为隐式参数引入的一种语法糖,使得隐式转换的编码更加简洁。
隐式参数
首先引入一个泛型函数max,用于取a和b的最大值
def max[T](a: T, b: T) = { if (a > b) a else b }
因为T是未知类型,只有运行时才会代入真正的类型,因此调用a > b是不正确的,因为T不确定,也就不确定T是否有>这个函数定义。
引入类型隐式转换,
因为Comparator类型是可比较较的,因此定义一个类型的隐式转换,将T转换为Comparator[T],
def max[T](a: T, b: T)(implicit m: T => Comparator[T]) = { if (m.compareTo(a,b)< 0) b else a }
使用:
class A(val weight: Int) object ContextBound { def max[T](a: T, b: T)(implicit m: T => Comparator[T]) = { if (m.compareTo(a,b)< 0) b else a } def main(args: Array[String]) { implicit def toComparator(obj: A) = new Comparator[A] { override def compare(o1: A, o2: A): Int = o1.weight - o2.weight; } println(max(new A(300), new A(400)).weight) }
上下文界定
Context Bound的目的是省略隐式值的书写:
def max[T](a: T, b: T)(implicit m:Comparator[T]) = { if (m.compareTo(a, b) < 0) b else a }
ContextBound:
存在一个隐式值,这个隐式对象以参数T为泛型参数,实现某种操作
package examples.scala.implicits import java.util.Comparator class A(val weight: Int) object ContextBound { def max[T: Comparator](a: T, b: T) = { val c = implicitly[Comparator[T]] if (c.compare(a, b) < 0) b else a } def main(args: Array[String]) { //implicitly查找的是类型为Comparator[T]的隐式值,而不是隐式类型转换函数 implicit val toComparator = new Comparator[A] { override def compare(o1: A, o2: A): Int = o1.weight - o2.weight; } println(max(new A(300), new A(400)).weight) } }
视图界定
存在一个类型转换函数,将T转换为Ordered[T]
object ViewBound { def max[T <% Ordered[T]](a: T, b: T) = { if (a.compare(b) < 0) b else a; } def main(args: Array[String]) { implicit def toOrdered(a: A) = new Ordered[A] { override def compare(that: A): Int = a.weight - that.weight } println(max(new A(300), new A(400)).weight) } }