Lorsque l'on parle de prendre une "méthode" de Swift ou ObjC (ou ruby ou java, ou...), ces méthodes ne sont pas vraiment privé. Il n'y a pas de réel contrôle d'accès autour d'eux. Une langue qui offre tout de même un peu d'introspection permet aux développeurs d'obtenir ces valeurs à partir de l'extérieur de la classe, si ils veulent vraiment.
Donc, ce que nous sommes réellement en train de parler ici est un moyen de définir un public interface simple présente les fonctionnalités que nous voulons, et "cache" du reste ce que nous considérons comme "privé".
La Swift mécanisme permettant de déclarer des interfaces est l' protocol
, et il peut être utilisé à cette fin.
protocol MyClass {
var publicProperty:Int {get set}
func publicMethod(foo:String)->String
}
class MyClassImplementation : MyClass {
var publicProperty:Int = 5
var privateProperty:Int = 8
func publicMethod(foo:String)->String{
return privateMethod(foo)
}
func privateMethod(foo:String)->String{
return "Hello \(foo)"
}
}
Rappelez-vous, les protocoles sont les premiers types de classe et peut être utilisé n'importe où un type peut. Et, lorsqu'il est utilisé de cette façon, ils n'exposent que leurs propres interfaces, et non pas ceux de la mise en œuvre de type.
Ainsi, aussi longtemps que vous utilisez MyClass
au lieu de MyClassImplementation
dans vos types de paramètres, etc. il devrait tout juste travail:
func breakingAndEntering(foo:MyClass)->String{
return foo.privateMethod()
//ERROR: 'MyClass' does not have a member named 'privateMethod'
}
Il y a certains cas de l'affectation directe où vous devez être explicite avec le type au lieu de s'appuyer sur Swift à déduire, mais cela ne semble guère un briseur d'affaire:
var myClass:MyClass = MyClassImplementation()
En utilisant des protocoles de cette façon, la sémantique, raisonnablement concis, et à mes yeux ressemble beaucoup à la Classe Extentions nous avons été en utilisant à cette fin en ObjC.