加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

Scala可以注意到路径依赖类型之间的身份吗?

发布时间:2020-12-16 10:03:08 所属栏目:安全 来源:网络整理
导读:有时在 Scala中我发现我得到与路径依赖类型相关的类型不匹配,但我可以轻易地推断出事实上类型是一致的.这是一个简单的例子: trait Foo { trait Bar }object Main extends App { val foo1 = new Foo { } val foo2 = foo1 def turkle(x: foo1.Bar) {} turkle(
有时在 Scala中我发现我得到与路径依赖类型相关的类型不匹配,但我可以轻易地推断出事实上类型是一致的.这是一个简单的例子:

trait Foo { trait Bar }

object Main extends App {
  val foo1 = new Foo { }
  val foo2 = foo1

  def turkle(x: foo1.Bar) {}

  turkle(new foo2.Bar {})
}

它给出:“类型不匹配;找到:需要Main.foo2.Bar的java.lang.Object:Main.foo1.Bar”.

当然,Main.foo1.Bar和Main.foo2.Bar路径必须重合,因为我们写了val foo2 = foo1.我们可以通过将最后一行更改为来验证这一点

turkle((new foo2.Bar {}).asInstanceOf[foo1.Bar])

这两个编译和运行没有例外.

Can Scala automatically perform reasoning like this? If so,how can I make this happen?

(如果没有,是否有任何前景可以向这个方向扩展类型系统?)

我会注意到Scala确实会出现这种推理.假设我将特性Foo改为对象Foo:

object Foo { trait Bar }

object Main extends App {
  val foo1 = Foo
  val foo2 = foo1

  def turkle(x: foo1.Bar) {}

  turkle(new foo2.Bar {})
}

现在一切都编译得很好:不知何故,Scala已经确定Main.foo1.Bar和Main.foo2.Bar与Foo.Bar真的相同.

解决方法

Iulian Dragos在最近的一个问题中给了 the answer you need.简短的版本是编译器不进行流分析,所以在你的第一个例子中它不能告诉foo1.Bar和foo2.Bar是相同的类型,因为foo1和foo2只是Foo类型.但是在第二个例子中,foo1被推断为单例类型Foo.type(Foo的子类型),因此事情按预期工作.

您可以通过将foo2声明为foo1的单例类型来使您的第一个示例工作:

val foo2:foo1.type = foo1

请参阅Scala语言规范2.9的第3.2.1节以供参考.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读