Mixins в Скала - PullRequest
       2

Mixins в Скала

2 голосов
/ 23 октября 2011

Я пытаюсь создать черту в Scala:

trait First {
  override def greet() {
    super.greet
    println("First")
  }
}

, но компилятор говорит:

scala/scala_learning/traits_hierarchy.scala:3: error: value greet is not a member of java.lang.Object with ScalaObject
    super.greet
          ^

Но я бы хотел расширить эту черту некоторым классом, который имеет суперклассСпособ приветствовать ... Возможно ли это в Scala?

Ответы [ 2 ]

5 голосов
/ 23 октября 2011

Несмотря на то, что в scala есть структурные типы, я не думаю, что вы можете сделать это для любого типа, у которого есть метод greet, но для метода greet в определенной характеристике или классе.

Тогда, если вы хотите, чтобы ваша подпрограмма изменила еще не определенную подпрограмму, вызывая ее с помощью super, она должна быть помечена abstract overrid e, а не просто переопределить.

Это было бы

trait Greeter { def greet }

trait First extends Greeter {
  abstract override def greet = {
    super.greet
    println("Hi, I'm first")
  }
}

Тогда вы можете иметь приветствие

class StandardGreeter(greeting: String) extends Greeter {
  def greet = println(greeting)
}

Обратите внимание, что First был определен без знания StandardGreeter. Вы смешиваете в новых классах с

class FirstGreeter(greeting: String) extends StandardGreeter(greeting) with First

или создайте экземпляры напрямую с помощью

new StandardGreeter("whatever") with First

Вы можете прочитать эту статью .

2 голосов
/ 24 октября 2011

Я полагаю, что вы можете сделать это со структурными типами себя:

trait Foobar {
    this: { def greet() } => // self type
    def go() = greet()
}
class Barbar extends Foobar { def greet() = { println("hello") }}

Вы определяете, что Foobar может расширять только класс, который определяет метод greet ().Используя REPL:

scala> trait Foobar { this: { def greet() } =>
     | def go() = greet()
     | }
defined class Foobar

scala> new Foobar()
<console>:9: error: class Foobar cannot be instantiated because it does not conform to its self-type Foobar with AnyRef{def greet(): Unit}
              new Foobar()
              ^

scala> class Barbar extends Foobar { def greet() = { println("hello") }}
defined class Barbar

scala> new Barbar().go
hello

Затем вы можете переопределить метод greet в Foobar (но для чего он нужен, я не знаю):

trait Foobar {
    this: { def greet() } => // self type
    override def greet() = { println("mygreet") }
    def go() = greet()
}
class Barbar extends Foobar
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...