3

我有这种代码

trait Outer1 {
  type Inner1
}

trait Outer2 {
  type Inner2

  val ev: Outer1#Inner1 =:= Inner2

  def f: Outer1#Inner1
}


object Main {

//  My Problem here  
//  def test1(o2: Outer2): o2.Inner2 =
//    o2.f                                  // <- type mismatch

  def test2(o2: Outer2): o2.Inner2 =
    o2.ev.apply(o2.f)
}

有没有机会让 test1 工作?为什么 Scala 编译器看不到ev并隐式应用它?

4

1 回答 1

3

两个问题:首先,您的证据参数不是隐式的,因此编译器也没有隐式发现:

trait Outer1 {
  type Inner1
}

trait Outer2 {
  type Inner2

  implicit val ev: Outer1#Inner1 =:= Inner2

  def f: Outer1#Inner1
}

第二个问题,值的成员不是标准隐式查找范围的一部分。所以你需要导入:

object Main {
  def test1(o2: Outer2): o2.Inner2 = {
    import o2.ev  // !
    o2.f
  }
}

编辑:尽管进行了抽象类型检查,但如果我没记错的话,您实际上无法实现 Outer2,因为您将如何提供证据证明其成员Inner2等于Outer1#Inner1何时Inner1是抽象的?这就是我要求具体场景的原因,因为从这个抽象的布局来看,我不确定你会到达任何地方。

据我所知,证据只对依赖类型有意义,例如

trait Outer1 {
  type Inner1
  def bar: Inner1
}

trait Outer2 {
  type Inner2
  val outer1: Outer1 { type Inner1 = Inner2 }

  def foo: Inner2 = outer1.bar
}
于 2013-06-02T17:03:49.997 回答