Как отладить и исправить расходящиеся последствия - PullRequest
0 голосов
/ 13 мая 2019

Я новичок в скале, и я пытаюсь обернуть голову вокруг расходящихся неявных расширений.

Вот мой игрушечный код:


class FooList[T](implicit ord: Ordering[T]) {

}

class Human(val score: Int) extends Ordering[Human] {


  override def compare(x: Human, y: Human): Int = {
    return x.score.compareTo(y.score);  
  }
}


object Main {

  def main(args: Array[String]): Unit = {
    val h = new Human(100)
    val lst = new FooList[Human]();
  }
}

Я получаю сообщение об ошибке:

diverging implicit expansion for type Ordering[Human]
starting with method comparatorToOrdering in trait LowPriorityOrderingImplicits


not enough arguments for constructor FooList: (implicit ord: Ordering[Human])FooList[Human].
Unspecified value parameter ord.

https://scastie.scala -lang.org / wkSrZ6BMQKW9ZJrsZhlITQ

Я бы хотел указатель или два в правильном направлении:)

1 Ответ

4 голосов
/ 13 мая 2019

Сообщение «расходящиеся» немного сбивает с толку, настоящая проблема заключается в непонимании того, как работают классы типов.Вот как это должно выглядеть:

class FooList[T](implicit ord: Ordering[T]) {
}

case class Human(score: Int)

implicit object HumanOrdering extends Ordering[Human] {
  def compare(x: Human, y: Human): Int =
    x.score.compareTo(y.score)
}

object Main {
  def main(args: Array[String]): Unit = {
    val h = new Human(100)
    val lst = new FooList[Human]()
  }
}

Обратите внимание, что класс Human - это просто простой тип данных.Существует отдельный implicit object, который реализует упорядочение для Human объектов путем расширения Ordering[Human].

. Главное в классе типов является то, что поведение не является частью исходного класса, а связано с нимсоздание значения implicit соответствующего типа.Это позволяет вам добавлять несколько классов поведения к классам, не изменяя сам базовый класс.


Обратите внимание, что вы можете поместить этот implicit object в объект класса, если вы хотите сделать вещи немного чище:

object Human {
  implicit object HumanOrdering extends Ordering[Human] {
    def compare(x: Human, y: Human): Int =
      x.score.compareTo(y.score)
  }
}
...