14.6面向對象小結
1、如何創建類
class 類名:
pass
2、創建方法
構造方法,init(self,arg)
obj = 類(‘a1‘)
普通方法
obj = 類(‘xxx’)
obj.普通方法名()
3、面向對象三大特性之一:封裝
class Bar:
def __init__(self, n,a):
self.name = n
self.age = a
self.xue = ‘o‘
b1 = Bar(‘a1‘, 123)
b2 = Bar(‘a2‘, 456)
4、適用場景:
如果多個函數中有一些相同參數時,轉換成面向對象。
5、面向對象三大特性之二:繼承
1、繼承
class 父類:
pass
class 子類(父類):
pass
2、重寫
防止執行父類中的方法
3、self永遠是執行該方法的調用者
4、
super(子類, self).父類中的方法(...)
父類名.父類中的方法(self,...)
5、Python中支持多繼承
- a. 左側優先
- b. 一條道走到黑
- c. 同一個根時,根最後執行
6、面向對象三大特性之三:多態
====> 原生多態
#Java string v = ‘a1‘ def func(string arg): print(arg) func(‘a1‘) func(123) # Python v = ‘a1‘ def func(arg): print(arg) func(1) func(‘a1‘)
============== 面向對象中高級==================
class Foo:
def __init__(self, name):
# 普通字段
self.name = name
# 普通方法
def show(self):
print(self.name)
obj = Foo(‘alex‘)
obj.name
obj.show()
類成員:
# 字段
- 普通字段,保存在對象中,執行只能通過對象訪問
- 靜態字段,保存在類中, 執行可以通過對象訪問 也可以通過類訪問
# 方法
- 普通方法,保存在類中,由對象來調用,self=》對象
- 靜態方法,保存在類中,由類直接調用,@staticmethod,
- 類方法,保存在類中,由類直接調用,cls=》當前類,@classmethod,也可以被對象調用
# 屬性,特性 - 不倫不類
應用場景:
如果對象中需要保存一些值,執行某功能時,需要使用對象中的值 -> 普通方法.
不需要任何對象中的值,靜態方法.
靜態字段
#靜態字段:可以類直接訪問,也可以對象訪問
class province:
country="china"
def __init__(self,name):
self.n=name
zhejiang=province("zhejiang")
print(province.country)
# china
print(zhejiang.country)
# china
# type是一個函數來來獲取類的類型,而__class__是類的屬性的方式來獲取類的類型
print(type(zhejiang))
# <class ‘__main__.province‘>
print(province.__class__)
# <class ‘type‘>
print(type(province))
# <class ‘type‘>
print(dir(province)) #dir(class):查看類的屬性(包括繼承的屬性)
# [‘__class__‘, ‘__delattr__‘, ‘__dict__‘, ‘__dir__‘, ‘__doc__‘, ‘__eq__‘, ‘__format__‘, ‘__ge__‘, ‘__getattribute__‘, ‘__gt__‘, ‘__hash__‘, ‘__init__‘, ‘__init_subclass__‘, ‘__le__‘, ‘__lt__‘, ‘__module__‘, ‘__ne__‘, ‘__new__‘, ‘__reduce__‘, ‘__reduce_ex__‘, ‘__repr__‘, ‘__setattr__‘, ‘__sizeof__‘, ‘__str__‘, ‘__subclasshook__‘, ‘__weakref__‘, ‘country‘]
print(province.__dict__) #class.__dict__: 屬性名:屬性值的鍵值對
# {‘__module__‘: ‘__main__‘, ‘country‘: ‘china‘, ‘__init__‘: <function province.__init__ at 0x0000002793B6D620>, ‘__dict__‘: <attribute ‘__dict__‘ of ‘province‘ objects>, ‘__weakref__‘: <attribute ‘__weakref__‘ of ‘province‘ objects>, ‘__doc__‘: None}
靜態方法和類方法
#靜態方法:可以不指定self,也可以指定self
#類方法:self為cls,指本類,可以被類直接調用,也可以被對象調用
class province1:
abc="test"
def info(self,population):
self.p=population
print(self.p)
print(self.abc)
@staticmethod
def country(args):
print("China")
print(args)
@classmethod
def citys(cls): #self指當前類
print("many citys!")
print(cls.abc)
obj1=province1()
province1.country(args="china1")
# China
# china1
province1.citys()
# many citys!
# test
obj1.citys()
# many citys!
# test
obj1.info(256)
# 256
# test
屬性
#屬性
class test:
@property
def func(self):
pass
@func.setter
def func(self,args):
print(args)
@func.getter
def func(self):
print("ok2")
@func.deleter
def func(self):
print("delete ok!")
obj2=test()
obj2.func
# ok2
obj3=test()
obj3.func=123
# 123
obj3.func
# ok2
del obj3.func
# delete ok!
屬性的第二種寫法
class foo:
def f1(self):
print("1")
def f2(self,val):
print(val)
def f3(self):
print("del")
a=property(fget=f1,fset=f2,fdel=f3,doc="test")
obj1=foo()
obj1.f2(100)
屬性應用:隨機翻頁
class page_turning:
def __init__(self,p):
self.page=p
@property
def start(self):
start_page=(self.page-1)*10+1
return start_page
@property
def end(self):
end_page=self.page*10+1
return end_page
def show(self):
for i in range(self.start,self.end):
print(i,end=" ")
while True:
ram=int(input("your choice:"))
page_turning(ram).show()
print()
# your choice:1
# 1 2 3 4 5 6 7 8 9 10
# your choice:4
# 31 32 33 34 35 36 37 38 39 40
# your choice:
成員修飾符(訪問權限)
類的所有成員分為:字段,方法
公有成員,在任何地方都能訪問
私有成員,只有在類的內部才能訪問
私有成員和公有成員的定義不同:私有成員命名時,前兩個字符是下劃線。(特殊成員除外,例如:init、call等)
私有成員和公有成員的訪問限制不同:
靜態字段:
公有靜態字段:類可以訪問,類內部可以訪問;派生類中可以訪問
私有靜態字段:僅類內部可以訪問
普通字段:
公有普通字段:對象可以訪問;類內部可以訪問;派生類中可以訪問
私有普通字段:僅類內部可以訪問
方法、屬性的訪問與上述方式相似,即,私有成員只能在類內部使用。
PS:私有成員若非要訪問的話,可以通過 對象._類__屬性名 來訪問。
私有普通字段
#私有普通字段
class foo2:
def __init__(self,name,sex):
self.n=name
self.__s=sex #私有普通字段
print(name,sex)
print(self.n,self.__s)
def fun2(self):
print(self.__s)
class foo22:
def fun1(self):
print(foo2.__init__(self,"jiaxin01","f"))
print(foo2.fun2(self))
obj2=foo22()
obj2.fun1()
# jiaxin01 f
# jiaxin01 f
# None
# f
# None
obj3=foo2("jiaxin","f")
# jiaxin f
# jiaxin f
obj3.fun2()
# f
print(obj3.n)
# jiaxin
print(obj3._foo2__s)
# f
私有靜態字段
#私有靜態字段
class foo3:
__abc=123
def fun1(self):
print(self.__abc)
def fun2(self):
print(self.__abc)
obj33=foo3()
obj33.fun1()
print(foo3._foo3__abc)
obj33.fun2()
# 123
# 123
# 123
私有普通方法
#私有普通方法
class hoo:
def __fun1(self):
print("f1")
return("f1 ok!")
def fun2(self):
print(self.__fun1())
obj4=hoo()
print(obj4._hoo__fun1())
# f1
# f1 ok!
obj4.fun2()
# f1
# f1 ok!
私有靜態方法,私有類方法
#私有靜態方法,私有類方法
class soo:
@staticmethod
def __fun1():
print("fun1 ok ")
@classmethod
def __fun2(cls):
print("fun2 ok ")
def show(self):
print(self.__fun1())
obj5=soo()
obj5.show()
# fun1 ok
# None
soo._soo__fun1()
# fun1 ok
soo._soo__fun2()
# fun2 ok
類的特殊成員:
_init_ 類()初始化.
_int_ int(對象)執行
_call_ 對象()執行 _call__函數.
_str\ print(對象)執行__str__函數
_add_ 多對象相加自動調用此函數
_dict_ 顯示類的成員
_getitem_ 配置切片或引索
_setitem_ 對引索賦值
_delitem_ 刪除某個元素
_iter_ 對象.__iter__有此方法為可叠代對象
metaclass
14.6面向對象小結