“`class declaration head` {val_name:Type =>`class body`}”的语法含义是什么?

时间:2011-11-07 00:39:22

标签: scala syntax

在阅读一些关于Scala的文章时,我发现了一些带有好奇语法的例子,我可能会错误地理解它     

class Child[C <: Child[C]] {
  some_name : C =>                   // here, what does it mean?
   var roomie : Option[C] = None

   def roomWith(aChild : C)= { 
     roomie = Some(aChild)
     aChild.roomie = Some(this) 
   }
}
class Boy extends Child[Boy]

我发现了类似特征的例子。

这是否意味着我在类范围内将this对象声明为C的类型?

3 个答案:

答案 0 :(得分:10)

这是一种自我类型的注释。

这意味着类Child必须是C类型,即创建必须满足给定类的继承依赖项。

一个小例子:

scala> trait Baz
defined trait Baz


scala> class Foo {
     | self:Baz => 
     | }
defined class Foo


scala> val a = new Foo
<console>:9: error: class Foo cannot be instantiated because it does not conform to its self-type Foo with Baz
       val a = new Foo
               ^

scala> val a = new Foo with Baz
a: Foo with Baz = $anon$1@199de181


scala> class Bar extends Foo with Baz
defined class Bar

在这种情况下,Foo也必须是Baz。 满足该要求,可以创建Foo实例。 此外,定义一个新类(在本例中为Bar)也需要它Baz

请参阅: http://www.scala-lang.org/node/124

答案 1 :(得分:3)

自我类型的一个非常有用的应用是CRTP(http://en.wikipedia.org/wiki/Curiously_recurring_template_pattern)的简洁实现,例如。

abstract class Base[Sub] {
  self:Sub =>
  def add(s:Sub) : Sub
}

case class Vec3(x:Double,y:Double,z:Double) extends Base[Vec3] {
  def add(that:Vec3) = Vec3(this.x+that.x, this.y+that.y, this.z+that.z)
}

试图“欺骗”继承是行不通的:

class Foo extends Base[Vec3] {
  add(v:Vec3) = v
}

//error: illegal inheritance;
//self-type Foo does not conform to Base[Vec3]'s selftype Base[Vec3] with Vec3
//      class Foo extends Base[Vec3] {

答案 2 :(得分:2)

除了JaimeJorge的响应中的继承要求之外,如果要从内部类引用外部实例,则可以使用self类型为外部实例指定名称:

scala> class Company(name: String) {
     |   company =>
     |   class Department(name: String) {
     |     override def toString = "Department "+ name +" of "+ company.name
     |   }
     | }
defined class Company

scala> val c = new Company("ACME")
c: Company = Company@56a57bb2

scala> val d = new c.Department("Marketing")
d: c.Department = Department Marketing of ACME