Scala类扩展{}

时间:2014-07-19 05:02:26

标签: scala types

我偶然遇到了奇怪的编译Scala语法:

class Some extends {
  def hi = println("hi")
}

专家:

  • 它是Scala支持的官方语法吗?
  • 这是否意味着只是扩展Object
  • 它是否以某种方式与#34; duck typing"?
  • 相关
  • 你知道这个有趣或棘手的用法吗?

感谢。

3 个答案:

答案 0 :(得分:7)

这实际上是Scala语法中的一个奇怪的怪癖。在开始课堂主体之前,允许使用无关的extends。以下是Scala Syntax Summary

中的相关部分
ClassDef          ::=  id [TypeParamClause] {ConstrAnnotation} [AccessModifier] 
                       ClassParamClauses ClassTemplateOpt 
ClassTemplateOpt  ::=  ‘extends’ ClassTemplate | [[‘extends’] TemplateBody]
ClassTemplate     ::=  [EarlyDefs] ClassParents [TemplateBody]

ClassTemplateOpt是课程参数之后的所有内容,在这种情况下是从extends开始的所有内容。通常使用extendsClassTemplateOpt的第一次更改,其中extends由父级或早期初始化程序跟随。但是,早期初始化程序不能包含def,并且无法将大括号的内容解释为父级。它不能是结构类型,因为hi有一个具体的定义。

第二次交替允许类参数紧跟在类体之后,而不使用extends。但是,允许使用可选的extends。 OP代码中的extends就是一个例子,它完全等同于没有可选extends的相同代码:

class Some {
  def hi = println("hi")
}

答案 1 :(得分:6)

这实际上只是一个语法上的意外(我认为)。 Scala允许early definitions看起来像

class Some extends {
  ...
} with ATrait

因此解析器也接受class Some extends { ... },相当于class Some { ... } (source)

答案 2 :(得分:-1)

是的,这是Scala的结构类型或更常见的鸭子打字。

object LoudDuck {
    def quack(): String = "QUACK"
}

object QuietDuck {
    def quack(): String = "quack"
}

object CowDuck {
    def quack(): String = "moo"
}

def quackMyDuck(duck: { def quack(): String }) {
    println(duck.quack())
}

scala>quackMyDuck(LoudDuck)
QUACK

scala>

scala>quackMyDuck(QuietDuck)
quack

scala>

scala>quackMyDuck(CowDuck)
moo

您还可以使用"类型"声明您的结构类型。关键字。

type Duck = { def quack(): String }

def quackMyDuck(duck: Duck) {
    println(duck.quack())
}