2013-04-09 14 views
12

Mam klasy w Scala, który obecnie jest skonstruowany w sposób standardowy:Scala Konstruktor Deprecation

class Test(int : Int) 
{ 
    override def toString() = "Test: %d".format(int) 
} 

Jednak chciałbym, aby przejść nad budową pośrednią poprzez obiektu towarzyszącego. Ponieważ biblioteka, którą modyfikuję, jest używana przez innych, nie chcę, aby konstruktor był prywatny od razu. Zamiast tego chciałbym go wycofać, a następnie wrócić i uczynić go prywatnym, gdy tylko ludzie będą mieli szansę zmienić ich użycie. Więc zmodyfikowałem swój kod w ten sposób:

object Test 
{ 
    def apply(int : Int) = new Test(int) 
} 

@deprecated("Don't construct directly - use companion constructor", "09/04/13") 
class Test(int : Int) 
{ 
    override def toString() = "Test: %d".format(int) 
} 

To jednak powoduje, że cała klasa przestaje istnieć.

scala> Test(4) 
<console>:10: warning: class Test in package foo is deprecated: Don't construct directly - use companion constructor 
     val res0 = 
     ^
res0: com.foo.Test = Test: 4 

Czy ktoś wie, czy Scala wspiera Wycofanie konstruktorów, a jeśli tak, jak to się robi?

Odpowiedz

10

This thread wydaje się opisać rozwiązanie:

object Test 
{ 
    def apply(int : Int) = new Test(int) 
} 


class Test @deprecated("Don't construct directly - use companion constructor", "09/04/13") (int : Int) 
{ 
    override def toString() = "Test: %d".format(int) 
} 

nie może spróbować go teraz jednak.

+1

(edytowane) To działa, ale nie jest absolutnie idealne, ponieważ podczas importowania tej klasy pojawia się ostrzeżenie o wycofaniu, ponieważ obiekt towarzyszący wywołuje przestarzałego konstruktora - jakiś pomysł na jego obejście? – paulmdavies

+0

Czy na pewno? Powinieneś otrzymać ostrzeżenie podczas kompilacji 'Test', ale nie podczas importowania. –

+0

Masz rację - tylko przy kompilacji. – paulmdavies

1

Pod względem mojego konkretnego przypadku, gdy wycofanie konstruktora powoduje ostrzeżenie o wycofaniu w czasie kompilacji z powodu obiektu towarzyszącego używającego przestarzałego konstruktora, kolega zasugerował, żebym podał drugi konstruktor za pomocą fikcyjnego parametru i wycofał go bez :

object Test 
{ 
    def apply(int : Int) = new Test(int, false) 
} 


class Test (val int : Int, dummy : Boolean) 
{ 
    @deprecated("Don't construct directly - use companion constructor", "09/04/13") 
    def this(int : Int) = this(int, false) 

    override def toString() = "Test: %d".format(int) 
} 

działa to, że nie będzie tylko ostrzeżenia amortyzacyjne jeśli użytkownik jest wywołanie przestarzałej konstruktora, ale oczywiście jest to nieprzyjemne - czy ktoś ma lepsze rozwiązanie?

+0

Doskonałe rozwiązanie to takie, które już dostarczył Jens Schauder –

+0

Ale to nie jest rozwiązanie w tym konkretnym przypadku - nie jest idealnym rozwiązaniem, aby poprosić użytkowników o zastąpienie czegoś, co ostrzega przed wycofaniem z czegoś innego, co ostrzega przed deprecjacją ...? – paulmdavies

+0

Myślałem, że już potwierdziłeś, że nie ostrzega o wycofaniu się z kodu klienta (dostajesz tylko ostrzeżenie, gdy ** ty ** kompilujesz 'Test')? –

Powiązane problemy