類的私有變量和私有方法
創(chuàng)新互聯(lián)主要從事成都網(wǎng)站建設(shè)、網(wǎng)站制作、網(wǎng)頁(yè)設(shè)計(jì)、企業(yè)做網(wǎng)站、公司建網(wǎng)站等業(yè)務(wù)。立足成都服務(wù)和碩,十多年網(wǎng)站建設(shè)經(jīng)驗(yàn),價(jià)格優(yōu)惠、服務(wù)專業(yè),歡迎來(lái)電咨詢建站服務(wù):028-86922220
在Python中可以通過(guò)在屬性變量名前加上雙下劃線定義屬性為私有屬性
特殊變量命名
1、 _xx 以單下劃線開(kāi)頭的表示的是protected類型的變量。即保護(hù)類型只能允許其本身與子類進(jìn)行訪問(wèn)。若內(nèi)部變量標(biāo)示,如: 當(dāng)使用“from M import”時(shí),不會(huì)將以一個(gè)下劃線開(kāi)頭的對(duì)象引入 。
2、 __xx 雙下劃線的表示的是私有類型的變量。只能允許這個(gè)類本身進(jìn)行訪問(wèn)了,連子類也不可以用于命名一個(gè)類屬性(類變量),調(diào)用時(shí)名字被改變(在類FooBar內(nèi)部,__boo變成_FooBar__boo,如self._FooBar__boo)
3、 __xx__定義的是特列方法。用戶控制的命名空間內(nèi)的變量或是屬性,如init , __import__或是file 。只有當(dāng)文檔有說(shuō)明時(shí)使用,不要自己定義這類變量。 (就是說(shuō)這些是python內(nèi)部定義的變量名)
在這里強(qiáng)調(diào)說(shuō)一下私有變量,python默認(rèn)的成員函數(shù)和成員變量都是公開(kāi)的,沒(méi)有像其他類似語(yǔ)言的public,private等關(guān)鍵字修飾.但是可以在變量前面加上兩個(gè)下劃線"_",這樣的話函數(shù)或變量就變成私有的.這是python的私有變量軋壓(這個(gè)翻譯好拗口),英文是(private name mangling.) **情況就是當(dāng)變量被標(biāo)記為私有后,在變量的前端插入類名,再類名前添加一個(gè)下劃線"_",即形成了_ClassName__變量名.**
Python內(nèi)置類屬性
__dict__ : 類的屬性(包含一個(gè)字典,由類的數(shù)據(jù)屬性組成)
__doc__ :類的文檔字符串
__module__: 類定義所在的模塊(類的全名是'__main__.className',如果類位于一個(gè)導(dǎo)入模塊mymod中,那么className.__module__ 等于 mymod)
__bases__ : 類的所有父類構(gòu)成元素(包含了一個(gè)由所有父類組成的元組)
以單下劃線(_)表明是標(biāo)準(zhǔn)庫(kù)的變量
雙下劃線(__) 開(kāi)頭表明是編譯器的變量
建議自己在命名的時(shí)候不要用下劃線開(kāi)頭,避免與標(biāo)準(zhǔn)庫(kù)中的命名沖突。
Python?用下劃線作為變量前綴和后綴指定特殊變量
_xxx 不能用 “from module import *” 導(dǎo)入
__xxx__ 系統(tǒng)定義名字
__xxx 類中的私有變量名
核心風(fēng)格:避免用下劃線作為變量名的開(kāi)始
因?yàn)橄聞澗€對(duì)解釋器有特殊的意義,而且是內(nèi)建標(biāo)識(shí)符所使用的符號(hào),我們建議程序員避免用下劃線作為變量名的開(kāi)始。
一般來(lái)講,變量名_xxx被看作是“私有的”,在模塊或類外不可以使用,當(dāng)變量是私有的時(shí)候,用_xxx 來(lái)表示變量是很好的習(xí)慣。因?yàn)樽兞棵鸰_xxx__對(duì)Python 來(lái)說(shuō)有特殊含義,對(duì)于普通的變量應(yīng)當(dāng)避免這種命名風(fēng)格。
“單下劃線” 開(kāi)始的成員變量叫做保護(hù)變量,意思是只有類對(duì)象和子類對(duì)象自己能訪問(wèn)到這些變量;
“雙下劃線” 開(kāi)始的是私有成員,意思是只有類對(duì)象自己能訪問(wèn),連子類對(duì)象也不能訪問(wèn)到這個(gè)數(shù)據(jù)。
以單下劃線開(kāi)頭(_foo)的代表不能直接訪問(wèn)的類屬性,需通過(guò)類提供的接口進(jìn)行訪問(wèn),不能用“from xxx import *”而導(dǎo)入;
以雙下劃線開(kāi)頭的(__foo)代表類的私有成員;
以雙下劃線開(kāi)頭和結(jié)尾的(__foo__)代表python里特殊方法專用的標(biāo)識(shí),如 __init__()代表類的構(gòu)造函數(shù)。
python中有五種下劃線命名;
(1)單前導(dǎo)下劃線: var
以單個(gè)下劃線開(kāi)頭的變量或方法僅供內(nèi)部使用,但是不強(qiáng)制執(zhí)行。通過(guò)類名.變量名依然可以引用,但是在使用通配符導(dǎo)入模塊(from 模塊 import *)時(shí),不能調(diào)用使用下劃線定義的函數(shù),而常規(guī)導(dǎo)入(import 模塊)是可以調(diào)用的。
(2)單末尾下劃線:var
當(dāng)最符合當(dāng)前函數(shù)的變量名被占用,則可以使用_來(lái)解決命名沖突。單個(gè)末尾下劃線(后綴)是一個(gè)約定,用來(lái)避免與Python關(guān)鍵字產(chǎn)生命名沖突。
(3)雙前導(dǎo)下劃線:_ var
雙下劃線前綴會(huì)導(dǎo)致Python解釋器重寫(xiě)屬性名稱,以避免子類中的命名沖突。
這也叫做名稱修飾(name mangling) - 解釋器更改變量的名稱,以便在類被擴(kuò)展的時(shí)候不容易產(chǎn)生沖突。
(4)雙前導(dǎo)和末尾下劃線: var
Python保留了有雙前導(dǎo)和雙末尾下劃線的名稱,用于特殊用途。 這樣的例子有, init 對(duì)象構(gòu)造函數(shù),或 call --- 它使得一個(gè)對(duì)象可以被調(diào)用。最好避免在自己的程序中使用以雙下劃線(“dunders”)開(kāi)頭和結(jié)尾的名稱,以避免與將來(lái)Python語(yǔ)言的變化產(chǎn)生沖突。
(5)單下劃線:
有時(shí)候單個(gè)獨(dú)立下劃線是用作一個(gè)名字,來(lái)表示某個(gè)變量是臨時(shí)的或無(wú)關(guān)緊要的。單個(gè)下劃線僅僅是一個(gè)有效的變量名稱,會(huì)有這個(gè)用途而已。
總結(jié):
參考: Python中下劃線的5種含義
單下劃線和雙下劃線在Python變量、類、模塊命名中都有不懂的含義,名稱中都各有其含義。有一些是程序員之間約定俗成的,Python解釋器不用強(qiáng)制其執(zhí)行,但有些Python解釋器會(huì)強(qiáng)制執(zhí)行。
本文從以下幾種不同使用方式,對(duì)下劃線的用途和含義進(jìn)行說(shuō)明:
1)變量
通常用于類內(nèi)部變量的命名,表明該變量是該類私用變量,外部不要去訪問(wèn)它,但也是可以訪問(wèn)到的。這只是程序員之間的一個(gè)約定俗成的做法,Python解釋器本身不會(huì)對(duì)它進(jìn)行限制。
我們創(chuàng)建一個(gè)類:
實(shí)例化A,并訪問(wèn)它的變量,aa._bar 也是可以訪問(wèn)的,但既然人家這么命名了,外部最好不要去訪問(wèn)了
2)函數(shù)和模塊
和變量一樣,這是一個(gè)私有函數(shù),不建議外部程序調(diào)用該函數(shù)。
我們創(chuàng)建一個(gè)腳本aa.py, 里面有2個(gè)函數(shù) _aa,bb:
導(dǎo)入aa,分別調(diào)用函數(shù) _aa和bb,bb 可以調(diào)用,但顯示無(wú) _aa
3)類
同變量和函數(shù)一樣,都是私有變量,外部最好不要調(diào)用
用來(lái)避免和Python內(nèi)置函數(shù)命名產(chǎn)生沖突,PEP8解釋了這個(gè)約定。
如class或def不能用作Python中的變量名稱,如果之間用,會(huì)提示錯(cuò)誤。如果你非要用它,可以 使用 class_或 def_。
還有一些函數(shù)名,如chr,chr()是Python內(nèi)置函數(shù),用來(lái)表示ascii碼對(duì)應(yīng)的字符他的輸入時(shí)數(shù)字,可以用十進(jìn)制,也可以用十六進(jìn)制。如果你非要它來(lái)表示染色體,可以用chr_來(lái)代替。當(dāng)然如果你直接使用它作為變量名,它也不會(huì)報(bào)錯(cuò),但最好不要這樣使用。
在python中定義私有變量只需要在變量名或函數(shù)名前加上 "__" (兩個(gè)下劃線),那么這個(gè)函數(shù)或變量就會(huì)成為私有的了。
在內(nèi)部,python使用一種 name mangling 技術(shù),將__var 替換成 _classname__var,因此在外部調(diào)用__var會(huì)找不到,代替它的是_classname_var。這種處理方式叫做名稱修飾(name mangling):解釋器更改變量的名稱,以便在類被擴(kuò)展的時(shí)候不容易產(chǎn)生沖突。
由雙下劃線前綴和后綴包圍的變量,不會(huì)應(yīng)用名稱修飾,因此不會(huì)被Python解釋器修改:
我們創(chuàng)建一個(gè)類B,dir() 查看類的所有屬性,發(fā)現(xiàn) 存在 __aa__
但是,Python保留了有雙前導(dǎo)和雙末尾下劃線的名稱,用于特殊用途。 如,__init__對(duì)象構(gòu)造函數(shù),或 __call__ 它使得一個(gè)對(duì)象可以被調(diào)用。所有我們盡量不要使用這種方式命名變量,以免和Python解釋器內(nèi)置的函數(shù)發(fā)生沖突。
_ 不加任何其他字符,單獨(dú)作為一個(gè)名字,用來(lái)表示某個(gè)臨時(shí)的或者無(wú)關(guān)緊要的變量。
舉例1: 表示一個(gè)臨時(shí)變量 。在下面的循環(huán)中,我們不需要獲取循環(huán)的索引,只是print n 行 'Hello World',可以用 "_" 來(lái)表示它只是一個(gè)臨時(shí)值:
舉例2: 表示一個(gè)不關(guān)心的變量 ,僅僅是個(gè)占位符變量,用來(lái)占位。mlist 列表中,我只想獲得1,2,4 位的變量,那 3 和 5 可以 用 _ 來(lái)占位
舉例3 : 表示由解釋器評(píng)估的最近一個(gè)表達(dá)式的結(jié)果 ,方便進(jìn)行查看。