несоответствие типов в Scala при использовании Reduce - PullRequest
0 голосов
/ 10 мая 2018

Может кто-нибудь помочь мне понять, что не так с кодом ниже?

case class Point(x: Double, y: Double)

def centroid(points: IndexedSeq[Point]): Point = {
  val x = points.reduce(_.x + _.x)
  val y = points.reduce(_.y + _.y)
  val len = points.length
  Point(x/len, y/len)
}

При запуске я получаю сообщение об ошибке:

Error:(10, 30) type mismatch;
 found   : Double
 required: A$A145.this.Point
  val x = points.reduce(_.x + _.x)
                            ^

Ответы [ 2 ]

0 голосов
/ 10 мая 2018

Если вы хотите использовать reduce, вам нужно уменьшить как x, так и y за один проход, как это

def centroid(points: IndexedSeq[Point]): Point = {
  val p = points.reduce( (s, p) => Point(s.x + p.x, s.y + p.y) )
  val len = points.length

  Point(p.x/len, p.y/len)
}

Если вы хотите вычислить x и y независимо, тогда используйте foldLeft вместо reduce, как это

def centroid(points: IndexedSeq[Point]): Point = {
  val x = points.foldLeft(0.0)(_ + _.x)
  val y = points.foldLeft(0.0)(_ + _.y)
  val len = points.length

  Point(x/len, y/len)
}

Возможно, это яснее, но обрабатывает points дважды, поэтому он может быть несколько менее эффективным.

0 голосов
/ 10 мая 2018

reduce, в данном случае, принимает функцию типа (Point, Point) => Point и возвращает Point.

Один способ вычисления центроида:

case class Point(x: Double, y: Double)

def centroid(points: IndexedSeq[Point]): Point = {
  val x = points.map(_.x).sum
  val y = points.map(_.y).sum
  val len = points.length
  Point(x/len, y/len)
}
...