Scala的类型不匹配:需要_ $ 1,其中类型_ $ 1 <:(Scala type mis

2019-10-22 05:05发布

我是一个新手,Scala和我现在面临一个问题,我无法理解和解决。 我写了一个通用的trait是这一个:

trait DistanceMeasure[P<:DbScanPoint] {
  def distance(p1:P, p2:P):Double
}

其中DbScanPoint很简单:

trait DbScanPoint extends Serializable {}

然后,我有扩展它们以下两类:

class Point2d (id:Int, x:Double, y:Double) extends DbScanPoint {
   def getId() = id
   def getX() = x
   def getY() = y
}

class EuclideanDistance extends DistanceMeasure[Point2d] with Serializable {

   override def distance(p1:Point2d,p2:Point2d) = {
      (p1.getX()-p2.getX())*(p1.getX()-p2.getX()) + (p1.getY()-p2.getY()) * (p1.getY()-p2.getY())
  }
}

并在最后我有这个类:

class DBScanSettings {

   var distanceMeasure:DistanceMeasure[_<:DbScanPoint] = new EuclideanDistance
   //...
}

我的问题是,如果当我写在我的测试主要是:

 val dbScanSettings = new DBScanSettings()
 dbScanSettings.distanceMeasure.distance(new Point2d(1,1,1), new Point2d(2,2,2))

我得到以下编译错误:

 type mismatch;
 [error]  found   : it.polito.dbdmg.ontic.point.Point2d
 [error]  required: _$1 where type _$1 <: it.polito.dbdmg.ontic.point.DbScanPoint

我不明白这是问题。 我做了一个非常类似的事情与其他类和我没有错误,那么这个错误的原因很不起眼的我。

可能有人帮助我吗?

谢谢。

UPDATE

我设法做什么,我需要的代码更改为:

trait DistanceMeasure {
  def distance(p1:DbScanPoint, p2:DbScanPoint):Double
}

很显然使所有的相关的变化。

Answer 1:

你的问题的心脏是您要定义distanceMeasure与生存型变种,所以该类型尚不完全清楚的编译器。 然后,要调用distance ,其是取类型的两个实例P <: DbScanPoint传递以两种Point2d实例。 现在,这些都是正确的类型背后的具体类distanceMeasure (新EuclideanDistance ),但是你的方式定义distanceMeasure (与存在),编译器不能强制执行Point2d情况下是正确的类型,在混凝土基础DistanceMeasure需要。

说为了讨论这不是一个新的EuclideanDistance ,你,而不是实例化一个完全不同的IMPL DistanceMeasure未采取Point2d实例,然后试图打电话distance他这样,你有在这里。 如果编译器不能强制底层阶级接受提供的参数,它会抱怨这样。

有一堆的方法来解决这个问题,并解决最终取决于你在你的类结构所需要的灵活性。 一种可能的方式是像这样:

trait DBScanSettings[P <: DbScanPoint] {
  val distanceMeasure:DistanceMeasure[P]
 //...
}

class Point2dScanSettings extends DBScanSettings[Point2d]{
  val distanceMeasure = new EuclideanDistance
}

然后进行测试:

val dbScanSettings = new Point2dScanSettings()
dbScanSettings.distanceMeasure.distance(new Point2d(1,1,1), new Point2d(2,2,2))

但是,如果没有我真正了解你有什么需要抽象层次,这将是由你来定义的重组要求。



文章来源: Scala type mismatch: required _$1 where type _$1 <: