『無為則無心』Python面向物件 — 60、魔法屬性
阿新 • • 發佈:2022-03-01
目錄1、魔法屬性
2、魔法屬性
3、魔法屬性
4、魔法屬性
5、魔法屬性
6、魔法屬性
7、魔法屬性
- 1、魔法屬性
__name__
- 2、魔法屬性
__bases__
- 3、魔法屬性
__mro__
- 4、魔法屬性
__doc__
- 5、魔法屬性
__module__
和__class__
- 6、魔法屬性
__dict__
- 7、魔法屬性
__slots__
Python 類中,凡是以雙下劃線 "__" 開頭和結尾命名的成員(屬性和方法),這些特殊成員存在著一些特殊含義,都被稱為類的特殊成員(特殊屬性和特殊方法)。
我們把特殊屬性也可以稱之為魔法屬性,或者內建類屬性。
1、魔法屬性__name__
__name__
是用來標識模組名字的一個系統變數。
這裡分兩種情況:
- 第一種情況指的是當前執行的模組,那麼當前模組
__name__
__main__
。 - 第二種情況指的是該模組是使用
import
匯入的模組,那麼這個被匯入模組的__name__
變數的值為該模組的檔名(去掉.py
)。
示例:
Demo1.py
檔案:
# 在當前檔案中直接呼叫__name__屬性
def my_func():
print("我的模組名是", __name__)
# __name__屬性在模組中可直接呼叫
# 在當期模組中呼叫
# 結果:我的模組名是 __main__
if __name__ == "__main__":
my_func()
Demo2.py
檔案:
# 匯入Demo1模組,使用模組中的my_func()方法 from Demo1 import * # 執行my_func()方法 # 結果:我的模組名是 Demo1 my_func()
2、魔法屬性__bases__
Python 為所有類都提供了一個__bases__
屬性,通過該屬性可以檢視該類的所有直接父類,該屬性返回所有直接父類組成的元組。(直接父類)
class A(object): pass class B(A): pass class C(B): pass class D(C,B,A): pass # 類名直接呼叫__bases__屬性 print(C.__bases__) print(D.__bases__) """ 輸出結果: (<class '__main__.B'>,) (<class '__main__.C'>, <class '__main__.B'>, <class '__main__.A'>) """
注意:在類的例項物件中沒有
__bases__
屬性。
3、魔法屬性__mro__
Python的每一個有父類的類,都有一個與方法解析順序相關的特殊屬性__mro__
屬性, 它是一個tuple
(元組), 裝著方法解析時的物件查詢順序,越靠前的優先順序越高。
執行下面的程式碼:
class A(object):
pass
class B(A):
pass
class C(B):
pass
# 類名直接呼叫__bases__屬性
print(C.__bases__)
print(C.__mro__)
"""
輸出結果:
(<class '__main__.B'>,)
(<class '__main__.C'>, <class '__main__.B'>, <class '__main__.A'>, <class 'object'>)
"""
說明:
__mro__
屬性和__bases__
屬性的區別。
__bases__
屬性是檢視當前類的直接父類,返回一個元組。
__mro__
屬性是指在有繼承關係中,包括單繼承,多重繼承,多層繼承中。使用super
呼叫父類的方法和屬性的時候,優先查詢的順序。
4、魔法屬性__doc__
作用:表示類的描述文件資訊。
class Person:
"""
這裡是類的描述類資訊。
"""
def func(self):
"""
這裡是類中方法的描述類資訊。
"""
pass
# 因為是屬性,不用加()
print(Person.__doc__)
輸出結果:
5、魔法屬性__module__
和__class__
__module__
屬性:表示當前操作的物件屬於哪個模組。
__class__
屬相:表示當前操作的物件的是由哪個類建立的。
# 定義一個類
class Person(object):
pass
obj = Person()
print(obj.__module__)
print(obj.__class__)
"""
輸出結果:
__main__ : 表示前擋模組
<class '__main__.Person'> : 表示該物件屬於當前模組中的Python類
"""
6、魔法屬性__dict__
列出類中或者物件中的所有成員,以字典的形式返回。這個屬性不用我們再類中覆寫,類和物件預設自帶。
class Person(object):
def __init__(self, name, age):
self.name = name
self.age = age
def tellMe(self):
print(f'我叫{self.name},今年{self.age}')
# 獲取類的所有成員
print(Person.__dict__)
# # 獲取物件的所有成員
obj1 = Person('美猴王', "18")
obj2 = Person('齊天大聖', "30")
print(obj1.__dict__)
print(obj2.__dict__)
"""
輸出結果 :
類的所有成員:
{'__module__': '__main__',
'__init__': <function Person.__init__ at 0x0000000002425828>,
'tellMe': <function Person.tellMe at 0x0000000002425A68>,
'__dict__': <attribute '__dict__' of 'Person' objects>,
'__weakref__': <attribute '__weakref__' of 'Person' objects>,
'__doc__': None}
注意:__weakref__,和垃圾回收機制,還有弱引用的知識點有關。
物件的所有成員:
{'name': '美猴王', 'age': '18'}
{'name': '齊天大聖', 'age': '30'}
"""
注意:從上面的結果可以看出,物件呼叫
__dict__
屬性,沒有看到物件中的方法。
- 類的例項屬性屬於物件,類的例項方法不屬於物件。也就是說
__dict__
屬性不列印處物件的中方法。- 類中的類屬性和方法等都屬於類。
7、魔法屬性__slots__
Python是動態語言,對於普通的類,可以為類的例項物件賦值任何屬性,這些屬性會儲存在__dict__
中。
而類中定義了__slots__
屬性,它僅允許動態繫結__slots__
裡邊定義的屬性。
示例:
# 建立一個Student類
class Student():
# 定義__slots__
__slots__ = ('name', 'age')
# 建立一個學生物件
stu = Student()
# 動態新增__slots__屬性中定義的屬性,可以新增
stu.name = '孫悟空'
stu.age = 18
# 而__slots__屬性中沒有定義的屬性,是新增不了的。
# 結果:AttributeError: 'Student' object has no attribute 'addr'
stu.addr = "北京"