定義: class 類名: - 定義了一個類 def 函數名(self): - 在類中編寫了一個"方法" pass 調用: x1 = 類名() - 建立了一個對象/實例化一個對象 x1.函數名() - 經過對象調用其中一個方法
self參數是python幫助咱們傳遞的,調用的是哪一個實例,self就指向誰python
__new__(self)構造方法算法
__init__(self)初始化ide
class Foo(object): def __init__(self, a1, a2): # 初始化方法 """ 爲空對象進行數據初始化 :param a1: :param a2: """ self.a1 = a1 self.a2 = a2 def __new__(cls, *args, **kwargs): # 構造方法 """ 建立一個空對象 :param args: :param kwargs: :return: """ return object.__new__(cls) # Python內部建立一個當前類的對象(初創時內部是空的.).
寫在類中的函數叫作方法,寫在類外面的就是函數函數
對象.xxx ->>> 方法spa
類.xxx ->>>函數3d
xxx ->>>函數code
打印查看:對象
方法 ->>> methodblog
函數 ->>>function繼承
代碼檢查
from types import MethodType, FunctionType def check(arg): """ 檢查arg是方法仍是函數? :param arg: :return: """ if isinstance(arg, MethodType): print('arg是一個方法') elif isinstance(arg, FunctionType): print('arg是一個函數')
將相關功能封裝到一個類中
class FuncOne: def func1(self): pass def func2(self): pass def func3(self): pass
將數據封裝到一個對象中
class FuncTwo: def __init__(self, para1, para2, para3): self.para1 = para1 self.para2 = para2 self.para3 = para3
爲了實現代碼的複用性
class FuncThree: def func1(self): pass class FuncFour(FuncThree): def func2(self): pass obj = FuncFour() obj.func1()
經典類和新式類:
python2:經典類和新式類(object)
python3:只有新式類
經典類的查找順序:深度優先
新式類的查找順序:C3算法(python2.3更新)
注意:super遵循的是__mro__執行順序
實例變量是類中方法中的變量,調用時須要經過對象
class FuncChange: def __init__(self, para1, para2): self.para1 = para1 self.para2 = para2 obj = FuncChange(1,2) print(obj.para1)
寫在類的裏面,類裏的方法外面,調用時經過類名
class ST: lst = [] def get_lst(self): self.lst.insert(0,33) return self.lst class TT(ST): lst = [11, 22] s1 = TT() s2 = TT() y1 = s1.get_lst() print(y1) y2 = s2.get_lst() print(y2) print(TT.lst)
class FuncChange: para_one = 123 def __init__(self, para1, para2): self.para1 = para1 self.para2 = para2 print(FuncChange.para_one)
類中普通的方法,包含self,經過對象調用
class FuncWay: def __init__(self, para1, para2): self.para1 = para1 self.para2 = para2 # 實例方法 def func1(self): print(self.para1) obj = FuncWay(1,2) obj.func1() # 實例方法調用
@staticmethod,無需使用對象中封裝的值,能夠本身傳參,且不須要self,經過類名執行
class FuncWay: def __init__(self, para1, para2): self.para1 = para1 self.para2 = para2 # 靜態方法 @staticmethod def func2(para3): print(para3) FuncWay.func2(1) # 靜態方法調用
@classmethod,包含cls,經過類名執行
class FuncWay: def __init__(self, para1, para2): self.para1 = para1 self.para2 = para2 # 類方法 @classmethod def func3(cls, para4): print(cls, para4) FuncWay.func3(1) # 類方法調用
經過方法改造而來,@property
只有一個參數self,調用時無需加括號,所以適用於無需傳參且有返回值時使用
class FuncProperty: @property def func(self): return 123 obj = FuncProperty() print(obj.func)
不管是類的變量,類的方法仍是類的屬性都有公有和私有,
公有就是在類的內外均可以調用,私有是隻能在類的內部調用,私有的建立是在命名時在名字前加"__"
class Foo: a1 = 1 __a2 = 2 def __init__(self, num): self.num = num self.__salary = 1000 def data(self): print(self.num+self.a1) obj1 = Foo(666) obj2 = Foo(999) print(obj1.num) print(obj1.a1) obj1.num = 18 obj1.a1 = 99 print(obj1.num) print(obj1.a1) print(obj2.a1) print(obj2.num+Foo.a1) print(obj2.num+obj1.a1) 運行結果: 666 1 18 99 1 1000 1098
class Foo: a1 = 1 __a2 = 2 def __init__(self, num): self.num = num self.__salary = 100 def data(self): print(self.num+self.a1) obj = Foo(666) print(obj.num) print(obj.a1) print(obj.__salary) print(obj.__a2) print(Foo.a1) print(Foo.__a2) 運行結果: 666 1 Error Error 1 Error
class Base: @classmethod def f3(cls): print(cls) def f1(self): print("base.f1") self.f3() class Foo(Base): def f2(self): print("foo.f2") self.f1() obj = Foo() obj.f2() 運行結果: foo.f2 base.f1 <class '__main__.Foo'>
class Base(object): def f1(self): print('調用了Base') class Foo(object): def f1(self): print('我是Foo') Base.f1(self) obj = Foo() obj.f1()
運行結果:
我是Foo
調用了Base
class Foo(object): def f1(self): super().f1() print('我是Foo') class Bar(object): def f1(self): print('我是Bar') class Info(Foo, Bar): pass obj = Info() obj.f1() 運行結果: 我是Bar 我是Foo
當對象.屬性沒有時,觸發__getattr__方法
class Foo(object):
def __init__(self, a1, a2):
self.a1 = a1 self.a2 = a2
def __init__(self, a1, a2): self.a1 = a1 self.a2 = a2 obj = Foo(1,2) print(obj.a1 + obj.a2) 運行結果: 3
class Foo(object):
def __init__(self, a1, a2):
self.a1 = a1 self.a2 = a2
def __call__(self, *args, **kwargs): print(11111, args, kwargs) return 123 #能夠有返回值 obj = Foo(1,2) ret = obj(6, 4, 2, k1=456) print(ret) 運行結果: 11111 (6, 4, 2) {'k1': 456} 123
class Foo(object):
def __init__(self, a1, a2):
self.a1 = a1 self.a2 = a2
def __getitem__(self, item): print(item) return 8 #有返回值 obj = Foo(1,2) ret = obj['wo'] print(ret) 運行結果: wo 8
class Foo(object):
def __init__(self, a1, a2):
self.a1 = a1 self.a2 = a2
def __setitem__(self, key, value): print(key, value, 111111111) #沒有返回值 obj = Foo(1,2) obj['k'] = "setitem" 運行結果: k setitem 111111111
class Foo(object):
def __init__(self, a1, a2):
self.a1 = a1 self.a2 = a2
def __delitem__(self, key): print(key) obj = Foo(1,2) del obj['wo'] 運行結果: wo
class Foo(object):
def __init__(self, a1, a2):
self.a1 = a1 self.a2 = a2
def __add__(self, other): return self.a1 + other.a2 obj = Foo(1,2) obj1 = Foo(1,2) obj2 = Foo(88,99) ret = obj2 + obj1 print(ret) 運行結果: 90
class Foo(object): def __init__(self, a1, a2): self.a1 = a1 self.a2 = a2 def __enter__(self): print('1111') return 999 def __exit__(self, exc_type, exc_val, exc_tb): print('22222') obj = Foo(1,2) with obj as f: print(f) 運行結果: 1111 999 22222
class UserInfo(object): pass class Department(object): pass class StarkConfig(object): def __init__(self,num): self.num = num def changelist(self,request): print(self.num,request) def run(self): self.changelist(999) class RoleConfig(StarkConfig): def changelist(self,request): print(666,self.num) class AdminSite(object): def __init__(self): self._registry = {} def register(self,k,v): self._registry[k] = v(k) site = AdminSite() site.register(UserInfo,StarkConfig) site.register(Department,StarkConfig) print(len(site._registry)) # 3 for k,row in site._registry.items(): row.run()
用字典反回形參和所傳實參
class Foo(object): def __init__(self, name, age): self.name = name self.age = age def func(self): pass obj1 = Foo('張三', 19) obj2 = Foo('李四', 20) print(obj1.__dict__) print(obj2.__dict__) 運行結果: {'name': '張三', 'age': 19} {'name': '李四', 'age': 20}
顯示註釋信息
class Foo(object): """ 返回此處的註釋信息 """ def __init__(self): pass def func(self): pass def __str__(self): return "F1" obj = Foo() print(obj.__doc__) 運行結果: 返回此處的註釋信息
打印對象時,顯示的是__str__內的字符串,因此看到str不必定就是str,只有type檢測出的str可信
class Foo(object): def __init__(self): pass def func(self): pass def __str__(self): return "F1" obj = Foo() print(obj, type(obj)) 運行結果: F1 <class '__main__.Foo'>
將不可迭代對象變爲可迭代對象
class Foo(object): def __init__(self, name, age): self.name = name self.age = age def func(self): pass def __iter__(self): return iter([11, 22, 33]) obj = Foo("張三", 18) for el in obj: print(el) 運行結果: 11 22 33
class Foo(object): def __init__(self, name, age): self.name = name self.age = age def func(self): pass def __iter__(self): yield 11 yield 22 yield 33 obj = Foo("張三", 18) for el in obj: print(el) 運行結果: 11 22 33
檢查第一個參數是不是第二個參數的子孫類
class Base(object): # 父 pass class Foo(Base): # 子 pass class Bar(Foo): # 孫 pass print(issubclass(Bar, Base)) print(issubclass(Bar, Foo)) 運行結果: True True
獲取當前對象是由那個類建立的
class Foo(object): pass obj = Foo() print(obj, type(obj)) if type(obj) == Foo: print('obj是Foo類型') 運行結果: <__main__.Foo object at 0x00000000021EB9E8> <class '__main__.Foo'> obj是Foo類型
檢查第一個參數(對象)是不是第二個參數(類及父類)的實例
class Base(object): pass class Foo(Base): pass class Tuu: pass obj1 = Foo() print(isinstance(obj1, Foo)) print(isinstance(obj1, Base)) print(isinstance(obj1, Tuu)) 運行結果: True True False
根據字符串的形式,去對象中找成員
if hasattr(handler,val): func_or_val = getattr(handler,val) # 根據字符串爲參數,去模塊中尋找與之同名的成員。 if isinstance(func_or_val,FunctionType): func_or_val() else: print(func_or_val)
from types import MethodType,FunctionType def func(i): if isinstance(i, MethodType) print("這是方法") elif isinstance(i, FunctionType) print("這是函數")
根據字符串的形式,去判斷對象中是否有成員
根據字符串的形式,動態的設置一個成員到內存中
根據字符串的形式,動態的刪除一個成員(內存中)
class Foo(object): def __init__(self): object.__setattr__(self, 'info', {}) # 在對象中設置值的本質 def __setattr__(self, key, value): self.info[key] = value def __getattr__(self, item): print(item+"123") return self.info[item] obj = Foo() obj.name = 'sb' print(obj.name)