2015-05-19 15 views
8

Mam klasę abstrakcyjną z domyślną wartością dla jej parametru. Nie chcę ponownie używać wartości domyślnej w konstruktorze wszystkich możliwych implementacji.Domyślny parametr dziedziczenia Scala w klasie nadrzędnej

abstract class Place(val place: String = "World") 
class Message(val message: String = "Hello", p: String) extends Place(p) { 
    override def toString = s"$message $place" 
} 

Co chcę uzyskać

new Message("Hi", "Universe") = "Hi Universe" // Ok 
new Message("Hi") = "Hi World" // Doesn't work, second parameter is required 
new Message() = "Hello World" // Doesn't work, second parameter is required 

uznałem za pomocą pomocniczego konstruktora z pominięciem drugiego parametru, ale to nie pomaga, ponieważ nie można nazwać Super konstruktorów poza głównym konstruktorem.

Chcę wiedzieć, jak to zrobić, lub dlaczego nie jest to możliwe. Nie szukam obejścia, jak nie używanie dziedziczenia.

Odpowiedz

1

można ponownie wykorzystać wartość domyślną w bardziej elegancki sposób:

object Place { 
    val defaultPlace = "World" 
} 
abstract class Place(val place: String = Place.defaultPlace) 
class Message(val message: String = "Hello", p: String = Place.defaultPlace) extends Place(p) { 
    override def toString = s"$message $place" 
} 
+0

prace. nie w postaci zamkniętej. Tutaj masz 3 obiekty do żonglowania (obiekt, streszczenie i klasa). W szczególności nie udziela się zaliczenia przedmiotu i abstraktów o tej samej nazwie. klasa Wiadomość musi wiedzieć o obiekcie Miejsce, więc użycie tego wymaga więcej okablowania, jeśli to ma jakiś sens. abstrakcja i beton powinny poradzić sobie z tym wszystkim. – Drew

3

Obawiam się, że to niemożliwe. Po prostu przekazujesz wartość do miejsca konstruktora, więc nie użyje wartości domyślnej, bez względu na jej wartość. Jeśli nie przeszkadza ci o var zamiast val, tutaj jest to wariant, który działa dla 3 przypadkach:

abstract class Place(var place: String = "World") 
class Message(val message: String = "Hello") extends Place() 
{ 
    def this(message: String, place: String) = { 
     this(message) 
     this.place = place 
    } 
    override def toString = s"$message $place" 
} 

Konstruktorzy Scala są trochę z IMHO bałagan. Czasami lepszą odpowiedzią jest użycie metod fabrycznych apply() na obiekcie towarzyszącym, które są bardziej elastyczne.

Powiązane problemy