欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Python中的self用法詳解

 更新時(shí)間:2024年02月27日 18:08:20   投稿:laozhang  
在本篇文章里小編給大家整理的是關(guān)于Python中的self用法以及實(shí)例內(nèi)容,需要的朋友們參考下。

在Python類(lèi)中規(guī)定,函數(shù)的第一個(gè)參數(shù)是實(shí)例對(duì)象本身,并且約定俗成,把其名字寫(xiě)為self。其作用相當(dāng)于java中的this,表示當(dāng)前類(lèi)的對(duì)象,可以調(diào)用當(dāng)前類(lèi)中的屬性和方法。

class是面向?qū)ο蟮脑O(shè)計(jì)思想,instance(也即是 object,對(duì)象)是根據(jù) class 創(chuàng)建的。

一個(gè)類(lèi)(class)應(yīng)該包含數(shù)據(jù)和操作數(shù)據(jù)的方法,通俗來(lái)講就是屬性和函數(shù)(即調(diào)用方法)。

類(lèi) class 中為啥用使用 self ?

在類(lèi)的代碼(函數(shù))中,需要訪問(wèn)當(dāng)前的實(shí)例中的變量和函數(shù),即訪問(wèn)Instance中的:

對(duì)應(yīng)的變量(property):Instance.ProperyNam,去讀取之前的值和寫(xiě)入新的值。

調(diào)用對(duì)應(yīng)函數(shù)(function):Instance.function(),即執(zhí)行對(duì)應(yīng)的動(dòng)作。

  • -> 而需要訪問(wèn)實(shí)例的變量和調(diào)用實(shí)例的函數(shù),當(dāng)然需要對(duì)應(yīng)的實(shí)例Instance對(duì)象本身。
  • -> 而Python中就規(guī)定好了,函數(shù)的第一個(gè)參數(shù),就必須是實(shí)例對(duì)象本身,并且建議,約定俗成,把其名字寫(xiě)為self。
  • -> 所以,我們需要self(需要用到self)。

首先,在Python中類(lèi)的定義:

在python中,類(lèi)是通過(guò)關(guān)鍵字 class 定義的:

class 后面緊跟類(lèi)名,即 Person,類(lèi)名通常大寫(xiě)字母開(kāi)頭,緊接著是(object),表示該類(lèi)是從哪個(gè)類(lèi)繼承下來(lái)的,通常,如果沒(méi)有合適的 繼承類(lèi),就使用 object 類(lèi),這是所有類(lèi)最終都會(huì)繼承的類(lèi)。

class Person(object):  
    pass

將 Person類(lèi)實(shí)例化,創(chuàng)建實(shí)例化是通過(guò) 類(lèi)名+() 實(shí)現(xiàn)的。

class Person(object):  
    pass
student = Person()  # 創(chuàng)建類(lèi)的實(shí)例化
print(student)
print(Person)

1564998074250982.png

可以看到,變量 student 指向的就是一個(gè) Person的 object,后面的 0x0000026EE434D8D0 是內(nèi)存地址,每個(gè) object 的地址都不一樣,而 Person 本身則是一個(gè)類(lèi)。

也可以給實(shí)例變量綁定屬性,比如:為 student 綁定 name 和 score 屬性

class Person(object):  
    pass
student = Person()
# print(student)
# print(Person)
student.name = "Gavin"   # 為實(shí)例變量 student 綁定 name 屬性  類(lèi)似于 賦值 操作
student.score = 100    # 為 其綁定 score 屬性
print(student.name)
print(student.score)

1564998103749356.png

上述的方法雖然可以為類(lèi)的實(shí)例變量綁定屬性,但是不夠方便和elegant , 由于類(lèi) 可以起到模板的作用,故在創(chuàng)建實(shí)例的時(shí)候,可以將我們認(rèn)為必須綁定 屬性 強(qiáng)制填寫(xiě)進(jìn)去,在python中,是通過(guò) 類(lèi)中通常都會(huì)使用的一個(gè)方法,即def __init__(self) 方法,在創(chuàng)建實(shí)例變量的時(shí)候,就把 name 和 score 等屬性綁上去。

class Person(object):  
    def __init__(self,name,score):    
        self.name = name    
        self.score = score    
student = Person('Gavin',100)  # 傳入 __init__ 方法中需要的參數(shù)
print(student.name)
print(student.score)

1564998122835969.png

傳入空參數(shù)的情況,會(huì)報(bào)錯(cuò):

class Person(object):  
    def __init__(self,name,score):    
        self.name = name    
        self.score = score    
student = Person()   # 此處應(yīng)該有參數(shù)傳入,卻沒(méi)有傳
print(student.name)
print(student.score)

1564998150891641.png

注意:

1、__init__ 方法的第一個(gè)參數(shù)永遠(yuǎn)是 self ,表示創(chuàng)建的實(shí)例本身,因此,在 __init__ 方法的內(nèi)部,就可以把各種屬性綁定到 self,因?yàn)?self 就指向創(chuàng)建的實(shí)例本身。

2、使用了 __init__ 方法,在創(chuàng)建實(shí)例的時(shí)候就不能傳入 空的參數(shù)了,必須傳入與 __init__ 方法匹配的參數(shù),但是 self 不需要傳,python解釋器會(huì)自己把實(shí)例變量傳進(jìn)去。

在類(lèi)中定義多個(gè)函數(shù)相互調(diào)用

class Person(object):  
    def __init__(self,x,y):    
        self.x = x    
        self.y = y      
    def add(self):    
        sum = self.x + self.y    
        return sum    
    def square(self):    
        squr = pow(self.x,2)+pow(self.y,2)    
        return squr  
    def add_square(self):    
        c = self.add()+self.square()    
        return c    
student = Person(3,4)
print(student.add())
print(student.square())
print('--------- 我是可愛(ài)的分割線-----------')
print(student.add_square())

1564998173728416.png

通過(guò)上述的例子可以看出,與普通的函數(shù)相比,在類(lèi)中定義的函數(shù)只有兩點(diǎn)不同:

1、第一個(gè)參數(shù)永遠(yuǎn)是 self ,并且調(diào)用時(shí)不用傳遞該參數(shù)

2、在類(lèi)中函數(shù)相互調(diào)用要加 self ,如上例中: c = self.add()+self.square(), 不加 self ,會(huì)報(bào)錯(cuò): 函數(shù)未定義,看下圖:

1564998195879408.png

除此之外,類(lèi)的方法和普通函數(shù)沒(méi)甚區(qū)別,當(dāng)然也可以使用 默認(rèn)參數(shù)、可變參數(shù)和關(guān)鍵字參數(shù),例子如下:

class Person(object):  
    def __init__(self,x,y):    
        self.x = x    
        self.y = y          
    def add(self,z=16):     # 設(shè)置 默認(rèn)變量 z =16,這只是個(gè)普通的局部變量,非實(shí)例變量,實(shí)例變量需要 self.z = z,這樣定義    
        sum = self.x + self.y + z    
        return sum    
    def square(self):    
        squr = pow(self.x,2)+pow(self.y,2)    
        return squr  
    def add_square(self,z):    # 調(diào)用時(shí)傳入變量,這也是個(gè)普通的局部變量,非實(shí)例變量     
        c = self.add()+self.square() + z    
        return c    
student = Person(3,4)
print(student.add())
print(student.square())
print('--------- 我是可愛(ài)的分割線-----------')
print(student.add_square(16))

1564998219495696.png

看了上述的例子可能還是不明白 self 到底是個(gè)什么鬼,為啥要使用 self 這鬼東西?沒(méi)關(guān)系,往下看:

其實(shí) self 這家伙簡(jiǎn)單的說(shuō)就是把 class 中 定義的 變量和函數(shù) 變成 實(shí)例變量和實(shí)例函數(shù),作為類(lèi) class 的成員,使得成員間能互相調(diào)用,而不需要從外部調(diào)用 數(shù)據(jù)(變量)和 方法(函數(shù)),以實(shí)現(xiàn)數(shù)據(jù)的封裝,以上面的 Person 類(lèi)為例:

創(chuàng)建實(shí)例的時(shí)候需要給出實(shí)例變量 x,y, 調(diào)用函數(shù)時(shí)給出 z ,調(diào)用很容易,卻不知道內(nèi)部實(shí)現(xiàn)的細(xì)節(jié)。

總之,類(lèi)是創(chuàng)建實(shí)例的模板,而實(shí)例則是一個(gè)一個(gè)具體的對(duì)象,各個(gè)實(shí)例擁有的數(shù)據(jù)都相互獨(dú)立、互不影響;方法是與實(shí)例綁定的函數(shù),和普通的函數(shù)不同,方法可以直接訪問(wèn)實(shí)例的數(shù)據(jù)。

其實(shí) self 中存儲(chǔ)的是實(shí)例變量和實(shí)例函數(shù)的屬性,可以理解為一個(gè)字典( dict ),如:{'name':'zhang','age':'18'}就是這些。

注意只有數(shù)據(jù)屬性,并沒(méi)有創(chuàng)建新的類(lèi)的方法。 類(lèi)----->通過(guò)實(shí)例化生成----對(duì)象---->(對(duì)象只是一串類(lèi)似于字典的數(shù)據(jù),沒(méi)有把類(lèi)的里的方法復(fù)制給你,python沒(méi)有new這個(gè)方法?。?/p>

class Person(object):  
    def __init__(self,x,y):    
        self.x = x    
        self.y = y          
    def add(self,z=16):   # 設(shè)置 z 為實(shí)例變量,即 self.z = z, z 是 class 的一個(gè)成員了,而非普通局部變量    
        self.z = z    
        sum = self.x + self.y + z # z雖然已被實(shí)例化,但是依然可以當(dāng)作 普通變量來(lái)用
        return sum    
    def square(self):    
        squr = pow(self.x,2)+pow(self.y,2)    
        return squr  
    def add_square(self):        
        c = self.add()+self.square() + self.z # 調(diào)用實(shí)例變量 z     
        return c    
student = Person(3,4)
print(student.add())
print(student.square())
print('--------- 我是可愛(ài)的分割線-----------')
print(student.add_square())
print(student.z)     # 函數(shù)add 中的 z 被實(shí)例化以后,就可以利用實(shí)例化的方法訪問(wèn)它

1564998257705196.png

通過(guò)這個(gè)例子可以看出, z 本來(lái)是 add() 函數(shù)的默認(rèn)形參,通過(guò)將其實(shí)例化,就可以在其他函數(shù)體內(nèi)調(diào)用實(shí)例變量z

被實(shí)例化以后,就可以利用實(shí)例化的方法訪問(wèn)它。

那么 self 到底是什么?

class Box(object):
  def __init__(self, boxname, size, color):
    self.boxname = boxname
    self.size = size
    self.color = color # self就是用于存儲(chǔ)對(duì)象屬性的集合,就算沒(méi)有屬性self也是必備的
  def open(self, myself):
    print('-->用自己的myself,打開(kāi)那個(gè)%s,%s的%s' % (myself.color, myself.size, myself.boxname))
    print('-->用類(lèi)自己的self,打開(kāi)那個(gè)%s,%s的%s' % (self.color, self.size, self.boxname))
  def close(self):
    print('-->關(guān)閉%s,謝謝' % self.boxname)
b = Box('魔盒', '14m', '紅色')
b.close()
b.open(b) # 本來(lái)就會(huì)自動(dòng)傳一個(gè)self,現(xiàn)在傳入b,就會(huì)讓open多得到一個(gè)實(shí)例對(duì)象本身,print看看是什么。
print(b.__dict__) # 這里返回的就是self本身,self存儲(chǔ)屬性,沒(méi)有動(dòng)作。

1564998302930831.png

self代表類(lèi)的實(shí)例,而非類(lèi);self 就是 對(duì)象/實(shí)例 屬性集合

Box 是個(gè)類(lèi)-----》self 實(shí)例化------》 b對(duì)象/ 實(shí)例

class 抽象體------》實(shí)例化------》對(duì)象/實(shí)例,含有屬性:{'boxname':'魔盒', ‘size’:‘14m’, 'color':'red'},即 self

self 看似是整個(gè)對(duì)象,實(shí)際上清楚地描述了類(lèi)就是產(chǎn)生對(duì)象的過(guò)程,描述了 self 就是得到了 對(duì)象,所以 self 內(nèi)的鍵值可以直接使用

正如自然界中一個(gè)有效的對(duì)象,必須包括:

1、描述對(duì)象的屬性;2、對(duì)象的方法

所以 self是必須的,也是對(duì)象中重要的特性。

看下面的代碼,感覺(jué)就更神奇了:

class Box(object):
  def myInit(mySelf, boxname, size, color):
    mySelf.boxname = boxname
    mySelf.size = size
    mySelf.color = color # 自己寫(xiě)一個(gè)初始化函數(shù),一樣奏效,甚至不用self命名。其它函數(shù)當(dāng)中用標(biāo)準(zhǔn)self
    return mySelf # 返回給實(shí)例化過(guò)程一個(gè)對(duì)象!神奇!并且含有對(duì)象屬性/字典
  # def __init__(self, boxname, size, color):
  #   self.boxname = boxname
  #   self.size = size
  #   self.color = color #注釋掉原來(lái)標(biāo)準(zhǔn)的初始化
  def open(self, myself):
    print(self)
    print('-->用自己的myself,打開(kāi)那個(gè)%s,%s的%s' % (myself.color, myself.size, myself.boxname))
    print('-->用類(lèi)自己的self,打開(kāi)那個(gè)%s,%s的%s' % (myself.color, myself.size, myself.boxname))
  def close(self):
    print('-->關(guān)閉%s,謝謝' % self.boxname)
# 經(jīng)過(guò)改造,運(yùn)行結(jié)果和標(biāo)準(zhǔn)初始化沒(méi)區(qū)別
b = Box().myInit('魔盒', '14m', '紅色')
# b = Box('魔盒', '14m', '紅色')#注釋掉原來(lái)標(biāo)準(zhǔn)的初始化方法
b.close()
b.open(b) # 本來(lái)就會(huì)自動(dòng)傳一個(gè)self,現(xiàn)在傳入b,就會(huì)讓open多得到一個(gè)實(shí)例對(duì)象本身,print看看是什么。
print(b.__dict__) # 這里返回的就是self本身,self存儲(chǔ)屬性,沒(méi)有動(dòng)作。

1564998324254354.png

換個(gè)角度來(lái)講,對(duì)類(lèi)的操作有:

1、定義屬性 ; 2、調(diào)用方法

對(duì)類(lèi)的反饋有:

1、得到屬性 ; 2、執(zhí)行方法

在 class 類(lèi)的函數(shù)中,為什么 self是必要的,因?yàn)?self 是對(duì)象的載體,可以理解成一個(gè)字典,看下面代碼:

class Box(object):
  def myInit(mySelf, boxname, size, color):
    print(mySelf.__dict__)#顯示為{}空字典
    mySelf.boxname = boxname
    mySelf.__dict__['aa'] = 'w'#甚至可以像字典一樣操作
    mySelf.size = size
    mySelf.color = color # 自己寫(xiě)一個(gè)初始化函數(shù),一樣奏效,甚至不用self命名。其它函數(shù)當(dāng)中用標(biāo)準(zhǔn)self
    return mySelf # 返回給實(shí)例化過(guò)程一個(gè)對(duì)象!神奇!并且含有對(duì)象屬性/字典
  # def __init__(self, boxname, size, color):
  #   self.boxname = boxname
  #   self.size = size
  #   self.color = color #注釋掉原來(lái)標(biāo)準(zhǔn)的初始化
  def open(self, myself):
    print(self)
    print('-->用自己的myself,打開(kāi)那個(gè)%s,%s的%s' % (myself.color, myself.size, myself.boxname))
    print('-->用類(lèi)自己的self,打開(kāi)那個(gè)%s,%s的%s' % (myself.color, myself.size, myself.boxname))
  def close(self):
    print('-->關(guān)閉%s,謝謝' % self.boxname)
# 經(jīng)過(guò)改造,運(yùn)行結(jié)果和標(biāo)準(zhǔn)初始化沒(méi)區(qū)別
b = Box().myInit('魔盒', '14m', '紅色')
# b = Box('魔盒', '14m', '紅色')#注釋掉原來(lái)標(biāo)準(zhǔn)的初始化方法
b.close()
b.open(b) # 本來(lái)就會(huì)自動(dòng)傳一個(gè)self,現(xiàn)在傳入b,就會(huì)讓open多得到一個(gè)實(shí)例對(duì)象本身,print看看是什么。
print(b.__dict__) # 這里返回的就是self本身,self存儲(chǔ)屬性,沒(méi)有動(dòng)作。

1564998355181754.png

注意此處的: mySelf.__dict__['aa'] = 'w' #甚至可以像字典一樣操作; 在 b.__dict__ 的結(jié)果中顯示為:'aa':'w'

故可以把 self 理解成存儲(chǔ) 實(shí)例化對(duì)象屬性的字典(dict), self 存儲(chǔ)屬性,而沒(méi)有動(dòng)作執(zhí)行。

self總是指調(diào)用時(shí)的類(lèi)的實(shí)例。

python 中一些特殊的實(shí)例變量:

1、私有變量(private),只有內(nèi)部可以訪問(wèn),外部不能訪問(wèn),私有變量是在名稱前以兩個(gè)下劃線開(kāi)頭,如:__name,其實(shí)私有變量也不是完全不能被外部訪問(wèn),不能直接訪問(wèn)是因?yàn)閜ython解釋器對(duì)外把 __name 變量改成了 _類(lèi)名__name,所仍然可以通過(guò) _類(lèi)名__name 來(lái)訪問(wèn) __name。

2、在Python中,變量名類(lèi)似__xxx__的,也就是以雙下劃線開(kāi)頭,并且以雙下劃線結(jié)尾的,是特殊變量,特殊變量是可以直接訪問(wèn)的,不是private變量,所以,不能用__name__、__score__這樣的變量名。

3、以一個(gè)下劃線開(kāi)頭的實(shí)例變量名,比如_name,這樣的實(shí)例變量外部是可以訪問(wèn)的,但是,按照約定俗成的規(guī)定,當(dāng)你看到這樣的變量時(shí),意思就是,“雖然我可以被訪問(wèn),但是,請(qǐng)把我視為私有變量,不要隨意訪問(wèn)”。

以上就是一文讀懂Python中的self的詳細(xì)內(nèi)容,更多請(qǐng)關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

最新評(píng)論