Quel est le but du self
mot en Python? Je comprends qu'il fait référence à l'objet spécifique créé à partir de cette classe, mais je ne vois pas pourquoi il doit explicitement être ajouté à chaque fonction en tant que paramètre. Pour illustrer, dans Ruby je peux faire ceci:
class myClass
def myFunc(name)
@name = name
end
end
Ce que je comprends assez facilement. Cependant en Python, je dois inclure self
:
class myClass:
def myFunc(self, name):
self.name = name
Quelqu'un peut-il me parler de cela? Ce n'est pas quelque chose que j'ai rencontré dans mon expérience (certes limitée).
@name
plus intuitif queself.name
? Ce dernier, l'OMI, est plus intuitif.@foo
etself.foo
sont également explicites car aucune résolution implicite ne doit se produire (par exemple en C ++, les membres d'instance peuvent être "implicitement" accédés sans "explicitement" utiliser des espaces de noms). La seule différence est que Ruby introduit une nouvelle sémantique (@), contrairement à Python. Le fait qu'une nouvelle sémantique valait ou non la quantité de verbosité évitée est purement subjectif. Cependant, il convient de noter que la plupart des langages modernes choisissent d'introduire un concept ici (par exemple php's $ this, JS's this).Réponses:
La raison que vous devez utiliser
self.
est que Python n'utilise pas la@
syntaxe pour faire référence aux attributs d'instance. Python a décidé de faire les méthodes de manière à ce que l'instance à laquelle la méthode appartient soit passée automatiquement, mais pas reçue automatiquement: le premier paramètre des méthodes est l'instance sur laquelle la méthode est appelée. Cela rend les méthodes entièrement identiques aux fonctions, et laisse le nom réel à votre discrétion (bien que ceself
soit la convention, et les gens vont généralement vous froncer les sourcils lorsque vous utilisez autre chose.)self
N'est pas spécial pour le code, c'est juste un autre objet .Python aurait pu faire autre chose pour distinguer les noms normaux des attributs - une syntaxe spéciale comme Ruby l'a fait, ou nécessitant des déclarations comme C ++ et Java, ou peut-être quelque chose d'encore plus différent - mais ce n'est pas le cas. Python est tout pour rendre les choses explicites, pour rendre évident ce qui est quoi, et bien qu'il ne le fasse pas entièrement partout, il le fait par exemple pour les attributs. C'est pourquoi l'attribution à un attribut d'instance doit savoir à quelle instance attribuer, et c'est pourquoi il a besoin
self.
.la source
cls
fait référence à l'objet de classe, pas à l'objet d'instancecls
etself
est utilisée conventionnellement pour les méthodes d'instance. Si je le voulais, je pourrais utiliserself
des méthodes de classe etcls
par exemple des méthodes. Je pourrais aussi utiliserbob
etfnord
si j'aimais.this
place deself
. Aself
une histoire que je ne connais pas dans les anciens langages de programmation?self
provient des conventions de Modula-3, voir cette réponse pour plus de détails sur ce choix. (Avertissement: sa mine).self
mot-clé (Smalltalk, 1980) est antérieur authis
mot - clé (de C ++). Voir: stackoverflow.com/questions/1079983/…Prenons une classe vectorielle simple:
Nous voulons avoir une méthode qui calcule la longueur. À quoi cela ressemblerait-il si nous voulions le définir à l'intérieur de la classe?
À quoi devrait-elle ressembler lorsque nous devions la définir comme une méthode / fonction globale?
Donc, la structure entière reste la même. Comment puis-je m'en servir? Si nous supposons un instant que nous n'avions pas écrit de
length
méthode pour notreVector
classe, nous pourrions le faire:Cela fonctionne car le premier paramètre de
length_global
, peut être réutilisé commeself
paramètre danslength_new
. Cela ne serait pas possible sans expliciteself
.Une autre façon de comprendre le besoin d'explicite
self
est de voir où Python ajoute du sucre syntaxique. Lorsque vous gardez à l'esprit que, fondamentalement, un appel commeest transformé en interne en
il est facile de voir où cela
self
s'intègre. Vous n'écrivez pas réellement de méthodes d'instance en Python; ce que vous écrivez, ce sont des méthodes de classe qui doivent prendre une instance comme premier paramètre. Et par conséquent, vous devrez placer le paramètre d'instance quelque part explicitement.la source
Vector.length_new = length_global
montre l' illustration.Disons que vous avez une classe
ClassA
qui contient une méthodemethodA
définie comme:et
ObjectA
est une instance de cette classe.Maintenant, quand
ObjectA.methodA(arg1, arg2)
est appelé, python le convertit en interne pour vous en tant que:La
self
variable fait référence à l'objet lui-même.la source
Lorsque les objets sont instanciés, l'objet lui-même est passé dans le paramètre self.
Pour cette raison, les données de l'objet sont liées à l'objet. Vous trouverez ci-dessous un exemple de la façon dont vous aimeriez visualiser les données de chaque objet. Remarquez comment «self» est remplacé par le nom des objets. Je ne dis pas que cet exemple de diagramme ci-dessous est tout à fait exact, mais il devrait, espérons-le, servir à visualiser l'utilisation de soi.
L'objet est passé dans le paramètre self afin que l'objet puisse conserver ses propres données.
Bien que cela ne soit pas tout à fait exact, pensez au processus d'instanciation d'un objet comme celui-ci: lorsqu'un objet est créé, il utilise la classe comme modèle pour ses propres données et méthodes. Sans passer son propre nom dans le paramètre self, les attributs et méthodes de la classe resteraient comme un modèle général et ne seraient pas référencés (appartiendraient) à l'objet. Ainsi, en passant le nom de l'objet dans le paramètre self, cela signifie que si 100 objets sont instanciés à partir d'une seule classe, ils peuvent tous garder une trace de leurs propres données et méthodes.
Voir l'illustration ci-dessous:
la source
J'aime cet exemple:
la source
self
du type de variable, mais aussi de celui-ci. Essayez de faire le premier exemple avec un entier simple au lieu d'une liste. Le résultat serait bien différent.a.foo
dans le premier exemple plutôt queA.foo
?foo
Appartient clairement à la classe ...a
etb
sont tous les deux des étiquettes (ou pointeurs) pourA()
(la classe).a.foo
fait référence à laA().foo
méthode de classe. Dans le deuxième exemple, cependant,a
devient une référence à une instance deA()
, comme le faitb
. Maintenant qu'ils sont des instances au lieu de l'objet de classe lui-même, self permet à lafoo
méthode d'opérer sur les instances.Je vais démontrer avec du code qui n'utilise pas de classes :
Les classes sont juste un moyen d'éviter de passer tout le temps dans cette "situation" (et d'autres choses intéressantes comme l'initialisation, la composition des classes, les métaclasses rarement nécessaires et la prise en charge de méthodes personnalisées pour remplacer les opérateurs).
Maintenant, montrons le code ci-dessus en utilisant la machinerie de classe python intégrée, pour montrer comment c'est fondamentalement la même chose.
[migré ma réponse à partir d'une question fermée en double]
la source
Les extraits suivants sont tirés de la documentation Python sur soi :
Pour plus d'informations, consultez le tutoriel de documentation Python sur les classes .
la source
En plus de toutes les autres raisons déjà mentionnées, il permet un accès plus facile aux méthodes remplacées; vous pouvez appeler
Class.some_method(inst)
.Un exemple où c'est utile:
la source
Son utilisation est similaire à l'utilisation du
this
mot - clé en Java, c'est-à-dire pour donner une référence à l'objet courant.la source
Python n'est pas un langage construit pour la programmation orientée objet contrairement à Java ou C ++.
Lors de l'appel d'une méthode statique en Python, on écrit simplement une méthode avec des arguments réguliers à l'intérieur.
Cependant, une méthode objet, qui vous oblige à créer une variable, qui est un animal, dans ce cas, a besoin de l'argument self
La méthode self est également utilisée pour faire référence à un champ variable dans la classe.
Dans ce cas, self fait référence à la variable animalName de toute la classe. N'OUBLIEZ PAS: Si vous avez une variable dans une méthode, self ne fonctionnera pas. Cette variable n'existe simplement que pendant l'exécution de cette méthode. Pour définir des champs (les variables de la classe entière), vous devez les définir EN DEHORS des méthodes de classe.
Si vous ne comprenez pas un seul mot de ce que je dis, alors Google "Programmation orientée objet". Une fois que vous aurez compris cela, vous n'aurez même plus besoin de poser cette question :).
la source
staticMethod()
etobjectMethod(self)
. Je voudrais ajouter que pour invoquer la première, diriez-vousAnimal.staticMethod()
, tout en ayantobjectMethod()
besoin d'une instance:a = Animal(); a.objectMethod()
def getAnimalName
pour ne pas encombrer la chaîne que vous essayez de renvoyer etself
fait référence à l'instance de la classe, pas à aucun champ à l'intérieur de celle-ci.Il est là pour suivre le zen Python «explicite vaut mieux qu'implicite». C'est en effet une référence à votre objet de classe. En Java et PHP, par exemple, cela s'appelle
this
.Si
user_type_name
est un champ sur votre modèle, vous y accédez parself.user_type_name
.la source
Tout d'abord, self est un nom conventionnel, vous pouvez mettre n'importe quoi d'autre (étant cohérent) à sa place.
Il fait référence à l'objet lui-même, donc lorsque vous l'utilisez, vous déclarez que .name et .age sont des propriétés des objets Student (notez, pas de la classe Student) que vous allez créer.
Le code est ici
la source
self
est une référence d'objet à l'objet lui-même, par conséquent, ils sont identiques. Les méthodes Python ne sont pas appelées dans le contexte de l'objet lui-même.self
en Python peut être utilisé pour traiter des modèles d'objets personnalisés ou quelque chose.la source
L'utilisation de l'argument, appelé conventionnellement,
self
n'est pas aussi difficile à comprendre que pourquoi est-elle nécessaire? Ou pourquoi le mentionner explicitement? C'est, je suppose, une question plus importante pour la plupart des utilisateurs qui recherchent cette question, ou si ce n'est pas le cas, ils auront certainement la même question à mesure qu'ils avancent dans l'apprentissage de python. Je leur recommande de lire ces quelques blogs:1: Utilisation de soi expliquée
Notez qu'il ne s'agit pas d'un mot clé.
2: Pourquoi l'avons-nous ainsi et pourquoi ne pouvons-nous pas l'éliminer comme argument, comme Java, et avoir un mot-clé à la place
Une autre chose que je voudrais ajouter est qu'un
self
argument optionnel me permet de déclarer des méthodes statiques à l'intérieur d'une classe, sans écrireself
.Exemples de code:
PS : cela ne fonctionne que dans Python 3.x.
Dans les versions précédentes, vous devez explicitement ajouter un
@staticmethod
décorateur, sinon l'self
argument est obligatoire.la source
Je suis surpris que personne n'ait élevé Lua. Lua utilise également la variable «self» mais elle peut être omise mais toujours utilisée. C ++ fait de même avec «this». Je ne vois aucune raison d'avoir à déclarer «self» dans chaque fonction, mais vous devriez toujours pouvoir l'utiliser comme vous le pouvez avec lua et C ++. Pour un langage qui se targue d'être bref, il est étrange qu'il vous oblige à déclarer l'auto-variable.
la source
Jetez un oeil à l'exemple suivant, qui explique clairement le but de
self
self
est utilisé / nécessaire pour distinguer les instances.Source: explication de l'auto-variable en python - Pythontips
la source
C'est parce que par la façon dont python est conçu, les alternatives ne fonctionneraient guère. Python est conçu pour permettre de définir des méthodes ou des fonctions dans un contexte où à la fois implicite
this
(à la Java / C ++) ou explicite@
(à la ruby) ne fonctionnerait pas. Prenons un exemple avec l'approche explicite avec les conventions python:Maintenant, la
fubar
fonction ne fonctionnerait pas car elle supposerait qu'ilself
s'agit d'une variable globale (etfrob
aussi). L'alternative serait d'exécuter des méthodes avec une portée globale remplacée (oùself
est l'objet).L'approche implicite serait
Cela signifierait que
myX
cela serait interprété comme une variable locale dansfubar
(et dansfrob
aussi). L'alternative ici serait d'exécuter des méthodes avec une portée locale remplacée qui est conservée entre les appels, mais cela supprimerait la possibilité de variables locales de méthode.Cependant, la situation actuelle fonctionne bien:
ici lorsqu'il est appelé en tant que méthode
frob
recevra l'objet sur lequel elle est appelée via leself
paramètre, etfubar
peut encore être appelé avec un objet en tant que paramètre et fonctionne de la même (il est le même queC.frob
je pense).la source
Dans la
__init__
méthode, self fait référence à l'objet nouvellement créé; dans d'autres méthodes de classe, il fait référence à l'instance dont la méthode a été appelée.soi, comme nom, n'est qu'une convention , appelez-la comme vous voulez! mais lorsque vous l'utilisez, par exemple pour supprimer l'objet, vous devez utiliser le même nom:,
__del__(var)
oùvar
était utilisé dans le__init__(var,[...])
Vous devriez aussi y jeter un œil
cls
pour avoir une vue d'ensemble . Ce message pourrait être utile.la source
self agit comme le nom d'objet actuel ou l'instance de classe.
la source
self
est inévitable.Il y avait juste une question qui devait
self
être implicite ou explicite.Guido van Rossum
résolu cette question en disantself
doit rester .Alors où
self
vivent-ils?Si nous nous en tenions à la programmation fonctionnelle, nous n'en aurions pas besoin
self
. Une fois que nous entrons dans la POO Python, nousself
y trouvons .Voici le cas d'utilisation typique
class C
avec la méthodem1
Ce programme produira:
Contient donc
self
l'adresse mémoire de l'instance de classe. Le but deself
serait de conserver la référence pour les méthodes d'instance et pour nous d'avoir un accès explicite à cette référence.Notez qu'il existe trois types différents de méthodes de classe:
la source
des documents ,
précédant cet extrait,
x = MyClass()
la source
c'est une référence explicite à l'objet instance de classe.
la source