一.isinstance和issubclass

  • isinstance(obj,cls)檢查是否obj是否是類(lèi) cls 的對(duì)象

  • issubclass(sub, super)檢查sub類(lèi)是否是 super 類(lèi)的派生類(lèi)

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn) View Code

輸出結(jié)果如下

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn) View Code

二.反射和相關(guān)的內(nèi)置函數(shù)

  • 反射是指程序可以訪問(wèn)、檢測(cè)和修改它自己本身狀態(tài)或者行為的一種能力(自省)。

  • 而在Python中,反射其實(shí)就是通過(guò)字符串的形式訪問(wèn)或者修改對(duì)象的屬性。這里的對(duì)象是指一切對(duì)象,類(lèi)本身也是一個(gè)對(duì)象。

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 1 class People: 2     country = 'china' 3     def __init__(self,name,sex): 4         self.name = name 5         self.sex = sex 6     def walk(self): 7         print('walk') 8 p1 = People('silver_bullet','male') 9 print(hasattr(p1,'name'))              #hasattr(*args, **kwargs) 驗(yàn)證有沒(méi)有該屬性10 print(getattr(p1,'sex'))               #getattr(object, name, default=None) 獲取一個(gè)屬性,可以設(shè)置default11 print(setattr(p1,'age',22))            #setattr(x, y, v) 設(shè)置一個(gè)屬性,返回值為None,所以用下面get方法驗(yàn)證12 print(getattr(p1,'age'))13 print(delattr(p1,'age'))               #delattr(x, 'y') is equivalent to del x.y 刪除一個(gè)屬性,返回值為None14 # print(getattr(p1,'age'))             #age屬性已經(jīng)被刪除掉15 setattr(p1,'show_name',lambda self:self.name+' is excellent')#增加一個(gè)函數(shù)屬性16 print(p1.show_name(p1))

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 

模塊級(jí)別的反射

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

1 import sys2 xxx = 1113 this_module = sys.modules[__name__]     #獲取當(dāng)前模塊4 print(hasattr(this_module,'xxx'))5 print(getattr(this_module,'xxx'))6 setattr(this_module,'yyy','12345')7 print(getattr(this_module,'yyy'))

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

反射的好處

  • 實(shí)現(xiàn)可插拔機(jī)制。可以事先定義好接口,接口只有在被完成后才會(huì)真正執(zhí)行,這實(shí)現(xiàn)了即插即用,這其實(shí)是一種‘后期綁定’,即你可以事先把主要的邏輯寫(xiě)好(只定義接口), 然后后期再去實(shí)現(xiàn)接口的功能。 

  • 動(dòng)態(tài)導(dǎo)入模塊(基于反射當(dāng)前模塊成員)。

1 import importlib2 t = importlib.import_module('time')     #通過(guò)字符串的形式導(dǎo)入模塊,推薦使用importlib3 print(t.time())                         #不推薦__import__(m),m為字符串,這個(gè)是python解釋器自己使用的

三.內(nèi)置函數(shù)(__attr__相關(guān))

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 1 class Foo: 2     '內(nèi)置函數(shù)__attr__的使用' 3     def __init__(self,name): 4         self.name = name                   #這個(gè)也會(huì)觸發(fā)__setattr__的執(zhí)行 5     def __setattr__(self, key, value):     #給屬性賦值都會(huì)觸發(fā)__setattr__,把key和value都賦值,可以做類(lèi)型判斷,彌補(bǔ)python沒(méi)有類(lèi)型限制 6         self.__dict__[key] = value         #直接在dict字典中添加相應(yīng)的鍵值對(duì)即可,key和value都為字符串 7         print('from __setattr__') 8     def __delattr__(self, item):           #del 操作會(huì)觸發(fā)這個(gè)內(nèi)置函數(shù) 9         self.__dict__.pop(item)            #直接在dict字典中刪除相應(yīng)的鍵值對(duì)即可10         print('from __delattr__',type(item))# type(item)--------->str11     def __getattr__(self, item):           #注意:屬性獲取不到,才會(huì)觸發(fā)這個(gè)內(nèi)置函數(shù)?。?!12         print('get__attr__---->{0},{1}'.format(item,type(item)))13 14 f = Foo('silver_bullet')                   #觸發(fā)__init__里就有一個(gè)賦值,即會(huì)觸發(fā)__settattr__15 f.time = 55516 print(f.__dict__)17 print(f.time)18 del f.time                                  #觸發(fā)__del__內(nèi)置函數(shù)19 print(f.__dict__)20 f.xxx                                       #這個(gè)才會(huì)觸發(fā)__getattr__的執(zhí)行,沒(méi)有找到xxx的屬性,而現(xiàn)在卻沒(méi)有報(bào)錯(cuò)

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

四.定制自己的數(shù)據(jù)類(lèi)型

  • 繼承的方式 

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 1 class my_list(list):                   #基于繼承 2     def __init__(self,seq): 3         for i in seq: 4             if not isinstance(i,str): 5                 raise TypeError('This is not a str list') 6             else: 7                 super().append(i) 8     def append(self, object: str): 9         if not isinstance(object,str):10             raise TypeError('must be str')11         super().append(object)12     @property13     def mid_value(self):14         mid_index = len(self)//215         return self[mid_index]16 17 l = my_list(['a'])18 print(l)19 l.append('1')20 print(l)21 print(l.mid_value)22 l.insert(0,4)23 print(l)

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

  • 授權(quán)的方式  

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 1 class my_list():                                 #基于授權(quán) 2     def __init__(self,seq): 3         for i in seq: 4             if not isinstance(i,str): 5                 raise TypeError('This is not a str list') 6         self.seq = list((seq))                    #使用一個(gè)中間屬性self.seq保存這個(gè)列表 7     def __str__(self):                            #override  __str__,才能夠打印列表的顯示,否則打印的是一個(gè)對(duì)象地址 8         return str(self.seq) 9     def append(self, object: str):               #重新定制這個(gè)append10         if not isinstance(object,str):11             raise TypeError('must be str')12         self.seq.append(object)                  #實(shí)際上是在這里使用13     @property14     def mid_value(self):                         #定制一個(gè)屬性,返回中間值。15         mid_index = len(self.seq)//216         return self.seq[mid_index]17     def __getattr__(self, item):                 #其余方法都使用list默認(rèn)的18         func = getattr(self.seq,item)            #直接返回getattr的函數(shù)名19         return func20     def __getitem__(self, item):                 #加上以下三個(gè)item操作,才能夠支持索引,切片,賦值和del刪除21         return self.seq[item]22     def __setitem__(self, key, value):23         self.seq[key] = value24     def __delitem__(self, key):25         self.seq.pop(key)26         27         28 l = my_list(['a'])29 print(l)30 l.append('1')31 print(l[1])32 print(l.mid_value)33 l.insert(0,4)34 l[0]='123'35 print(l)36 print(l[1:])

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 

五.給日志文件加時(shí)間頭

使用授權(quán)的方式重寫(xiě)open

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 1 import time 2 class Open: 3     'override File  write' 4     def __init__(self,path,mode = 'r',encoding = 'GBK'): 5         self.fw = open(path,mode=mode,encoding=encoding)        #這里要寫(xiě)成位置參數(shù)的形式,取到文件句柄賦值給self.f 6     def write(self,line): 7         now_time = time.strftime('%Y-%m-%d-%X')                 #字符串形式顯示time時(shí)間 8         self.fw.write('{0}\n'.format(now_time))                 #添加日志文件的時(shí)間頭 9         self.fw.write(line)                                     #寫(xiě)想要輸入到文件里面的內(nèi)容10     def __getattr__(self, item):                                #不想要改寫(xiě)的地方定義在__getattr__中,找不到的屬性會(huì)觸發(fā)這個(gè)內(nèi)置函數(shù)11         func = getattr(self.fw,item)                            #通過(guò)getattr的方法,將函數(shù)名的入口地址獲取到并且返回12         return func13 14 f = Open('a.txt','w+')                                           #觸發(fā)__init__方法15 for i in range(2):16     f.write('11111111111\n')17     time.sleep(0.5)18 f.seek(0)19 print(f.readlines())

Android培訓(xùn),安卓培訓(xùn),手機(jī)開(kāi)發(fā)培訓(xùn),移動(dòng)開(kāi)發(fā)培訓(xùn),云培訓(xùn)培訓(xùn)

 

http://www.cnblogs.com/yangming111/p/6758328.html