2010-10-22 8 views
3

Je suis assez nouveau pour Scala, venant d'un arrière-plan Java de base. J'ai regardé comment implémenter des constructeurs de classe et comment fournir une certaine logique dans le setter pour un champ de cette classe.Classe Constructeur/Setter

class SetterTest(private var _x: Int) { 
    def x: Int = _x 
    def x_=(x: Int) { 
     if (x < 0) this._x = x * (-1) 
    } 
} 

Le paramètre constructeur est affecté au champ _x donc le poseur est pas utilisé. Que faire si je veux utiliser la logique du setter?

object Test { 
    def main(args: Array[String]) { 
     val b = new SetterTest(-10) 
     println(b.x) // -10 
     b.x = -10 
     println(b.x) // 10 
    } 
} 

En Java, j'aurais pu utiliser le setter dans le constructeur pour forcer l'utilisation de cet exemple de logique.

Comment est-ce que j'obtiendrais ceci dans scala?

Répondre

6

Dans Scala, l'ensemble du corps de classe constitue le constructeur principal. Ainsi, vous pouvez simplement faire ceci:

class SetterTest(private var _x: Int) { 
    x = _x // this will invoke your custom assignment operator during construction 

    def x: Int = _x 
    def x_=(x: Int) { 
    if (x < 0) this._x = x * (-1) 
    } 
} 

maintenant essayer:

scala> new SetterTest(-9).x 
res14: Int = 9 
+3

Oui, c'est l'un des points sensibles de Scala. Vous pouvez avoir soit le court code succinct sans setters, soit un bloat de type Java avec setters. Le problème est que le compilateur ne le reconnaît pas si vous définissez vous-même les setters/getters et échouerez avec un message d'erreur non utile. De plus, la définition de membres d'une classe via le constructeur contourne toute méthode de définition définie, en violation du principe d'accès unifié. C'est l'un des points noirs de Scala ... – soc

+0

@ pelotom: Merci pour une solution rapide. @soc +1 pour avoir apporté d'autres idées pour m'aider à évaluer ce que j'apprends. – rdoubleui