Подтвердить что ты не робот

Что такое неявные объекты?

Я читал о типах классов, где упоминались неявные объекты:

object Math {
  trait NumberLike[T] {
    def plus(x: T, y: T): T
    def divide(x: T, y: Int): T
    def minus(x: T, y: T): T
  }
  object NumberLike {
    implicit object NumberLikeDouble extends NumberLike[Double] {
      def plus(x: Double, y: Double): Double = x + y
      def divide(x: Double, y: Int): Double = x / y
      def minus(x: Double, y: Double): Double = x - y
    }
    implicit object NumberLikeInt extends NumberLike[Int] {
      def plus(x: Int, y: Int): Int = x + y
      def divide(x: Int, y: Int): Int = x / y
      def minus(x: Int, y: Int): Int = x - y
    }
  }
}

Что это? Где они описаны? Я нашел определение неявных классов на веб, но не для неявных объектов.

4b9b3361

Ответ 1

В Scala объекты и значения обрабатываются в основном одинаково. Неявный объект можно рассматривать как значение, которое находится в процессе поиска неявного его типа.

В вашем примере, если один неявно ищет класс типа NumberLike с параметром типа Double или Int, вы найдете NumberLikeDouble и NumberLikeInt.

implicit object NumberLikeDouble extends NumberLike[Double]

таким образом, примерно совпадает с

implicit val NumberLikeDouble: NumberLike[Double] = new NumberLike[Double] { ...}

или

implicit def NumberLikeDouble: NumberLike[Double] = new NumberLike[Double] { ...}

Как и val, существует только одно значение этого типа, и инстанцирование не требуется.


Простой вариант:

import Math.NumberLike

def sum[A](x: A, y: A)(implicit nl: NumberLike[A]) = nl.plus(x, y)

sum(4, 5)   // finds NumberLikeInt

Ответ 2

Благодаря неявным объектам вы можете определить:

def mymethod[T : NumberLike](value: T): T = {
  implicitly[NumberLike[T]].plus(value, value)
}

который позволяет вам называть ваши методы в Double и Floats, потому что у вас есть объекты для их обработки.

scala> mymethod(1.0)
res0: Double = 2.0

scala> mymethod(2)
res0: Int = 4

scala> mymethod("test") //Error