What is the reason that
trait Dog {
def bark = "woof"
}
object Dog extends Dog
works, but the following does not
trait Dog {
def bark = "woof"
}
class Dog extends Dog
I read somewhere that in the first case mentioned above the object is not a companion object. What is the scenario when object and trait should have the same name ?
From introduction to Chapter 2 (Identifiers, Names & Scopes):
There are two different name spaces, one for types and one for terms.
Section 5.5 (Object definitions) contains almost exactly your example (with Point
instead of Dog
), with the following comment:
Note that the double use of the name
Point
is legal, since the class definition defines the name Point in the type name space, whereas the object definition defines a name in the term namespace.
(emphasis mine)
Your second example with class Dog extends Dog
does not work, because both the class Dog
and trait Dog
end up in the namespace for types, and this results in a conflict.
Companion object
s are used whenever you would use static methods in e.g. Java (except that companion objects are much nicer, because they are, well, objects, and can be passed around as ordinary values).
The situation object Foo extends Foo
appears somewhat contrived and rather uncommon. Have you an actual example where it is used? If not, then it's just a corner case that is formally valid, simply because it's not explicitly prohibited.
EDIT: object AnsiColor extends AnsiColor
seems to be one of the most "important" applications of the object X extends X
pattern.