Understanding the use of self in Python

Source: Internet
Author: User
When I first started to learn Python's class writing, I found it very troublesome, why we need to call when the definition is not needed, why not internal simplification to reduce the number of keystrokes we hit? You will understand all the questions after reading this article.

Self represents an instance of a class, not a class.

Example to illustrate:

Class Test:  def prt (self):    print (self)    print (self.__class__) t = Test () t.prt ()

Execution results are as follows

<__main__. Test object at 0x000000000284e080><class ' __main__. Test ' >

As can be seen from the above example, self represents an instance of a class. The Self.class, however, points to the class.

Self does not have to be written self

There are many children's shoes to learn other languages and then learn python, so always feel self strange, want to write this, can you?

Sure, or rewrite the code above.

Class Test:  def prt (this):    print (this)    print (this.__class__) t = Test () t.prt ()

After you change this, the result is exactly the same.

Of course, it is better to respect the customary custom and use self.

Can self not write?

Inside the Python interpreter, when we call T.prt (), Python is actually interpreted as test.prt (t), which means to replace self with an instance of the class.

Interested children's shoes can rewrite the above t.prt () line, the actual results after the run is exactly the same.

In fact, it has been partly explained that self cannot be omitted when defined, so if you want to try it, see below:

Class Test:  def prt ():    print (self) t = Test () t.prt ()

The runtime reminder error is as follows: PRT does not have parameters when it is defined, but we are forced to pass a parameter when we run it.

Since the above explained that T.prt () is equivalent to TEST.PRT (t), the program reminds us to pass a parameter T more.

Traceback (most recent): File "h.py", line 6, in <module>  t.prt () typeerror:prt () takes 0 positional a Rguments but 1 was given

Of course, this is the class method if neither of our definitions nor the invocation is capable of passing class instances.

Class Test:  def prt ():    print (__class__) test.prt ()

The operation results are as follows

<class ' __main__. Test ' >

In inheritance, which instance is passed in, which is the incoming instance, not the instance of the class that defines self.

Look at the code first

Class Parent:  def pprt (self):    print (self) class child (Parent):  def cprt (self):    print (self) c = child () C.cprt () c.pprt () p = Parent () p.pprt ()

The operation results are as follows

<__main__. The child object is at 0x0000000002a47080><__main__. The child object is at 0x0000000002a47080><__main__. Parent Object at 0x0000000002a47240>

Explain:

The problem should not be understood when running c.cprt (), referring to an instance of the child class.

However, when running C.pprt (), it is equivalent to CHILD.PPRT (c), so self refers to an instance of the child class, and because the Pprt () method is not defined in self, the Pprt () method is defined in the parent class, as it is found on the inheritance tree. So it will be successfully called.

In a descriptor class, self refers to an instance of a descriptor class

Not very easy to understand, first look at the example:

Class Desc:  def __get__ (self, INS, CLS):    print ("Self" desc:%s '% self)    print (self, ins, CLS) class Test:
  x = Desc ()  def prt (self):    print (' Self in Test:%s '% self) t = Test () t.prt () t.x

The results of the operation are as follows:

Self in Test: <__main__. Test object at 0x0000000002a570b8>self in Desc: <__main__. Desc object at 0x000000000283e208><__main__. Desc object at 0x000000000283e208> <__main__. Test object at 0x0000000002a570b8> <class ' __main__. Test ' >

Most children's shoes are starting to have doubts, why is self defined in the Desc class not supposed to be the instance t that calls it? How does it become an instance of the Desc class?

Note: It's important to keep your eyes open, The call here is T.x, which is the property x of the instance T of the test class, because the attribute x is not defined in the instance T, so the class attribute x is found, and the property is a descriptor property, an instance of the Desc class, so there is no method for test.

Then we can get the same result if we call property X directly through the class.

Here is the result of changing the t.x to Test.x run.

Self in Test: <__main__. Test object at 0x00000000022570b8>self in Desc: <__main__. Desc object at 0x000000000223e208><__main__. Desc object at 0x000000000223e208> None <class ' __main__. Test ' >

Digression: Because in many cases the descriptor class still needs to know who the instance that called the descriptor is, so there is a second argument in the Descriptor class, INS, which is used to represent the class instance that called it, so t.x can see the second item in the third row in the run result as <main. Test object at 0x0000000002a570b8>. When called with Test.x, none is returned because there are no instances.

Understanding self in Python from the nature of OO
Give me a chestnut, suppose I want to manipulate the user's data, the user's data contains name and age. If you use process-oriented, the implementation is the following.

def user_init (user,name,age):   user[' name '] = name   user[' age ' = Age  def set_user_name (user, X):   user[ ' name '] = x  def set_user_age (user, X):   user[' age ') = x  def get_user_name (user):   return user[' name ']  def get_user_age (user):   return user[' age '  myself = {} User_init (myself, ' kzc ', +) print get_user_age ( myself) Set_user_age (myself,20) print get_user_age (myself)

It can be seen that the user's various operations, all of them to pass user parameters in.
If you use object-oriented, you do not have to pass the user parameters every time, the relevant data and operations in a single place, in this class in various places, you can easily get data.
The reason why the data can be accessed in various places in the class is that it is bound to self, and the first parameter of the method, of course, can not be called self, other names, self is only a contract.
The following is an object-oriented implementation, you can see, more structured, clear and readable.

Class User (object):   def __init__ (self,name,age):     self.name = name     Self.age = Age    def SetName (self, Name):     self.name = name    def setage (self,age):     Self.age = Age    def GetName (self):     return Self.name    def getage (self):     return self.age  u = User (' kzc ', +) print u.getname () print u.getage ()

From the above example can be seen, in fact, object-oriented is very useful, but most people are abstract bad, encapsulation of bad, the use of the wrong.

Summarize

    • Self is defined when it is defined, but is automatically passed in when it is called.

    • Self's name is not a rule of death, but it is best to use self as agreed.

    • Self always refers to an instance of the class at the time of invocation.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.