set去重應用

1.其中涉及__hash__與__eq__這兩個內置方法.算法

2.列如: 要求用類生成多個對象,其中姓名和性別相同的對象可認爲是同一我的,用set原理作去重app

class People:函數

    def __init__(self,name,age,sex):spa

        self.name=name對象

        self.age=age內存

        self.sex=sex字符串

    def __hash__(self):         對象找自帶的hash算法,set的算法是算所有,如今改成了算自定義的部分hash

        res=hash(self.name+self.sex)it

        return  res                   返回的hash值和原數據類型作綁定再加入集合中,如需取出則給出原數據類型class

    def __eq__(self,other):   發現重複的hash值自動觸發,並把重複的這兩個拿出來作對比

        if self.name+self.sex==other.name+other.sex:   set對比的是所有,如今對比的是自定義的部分

           return  True              如返回True則拋棄,Flase則從新計算並加入.

people_lis=[]

for  i  in  range(1,200):

    people_lis.append(People(‘張三’, i ,’男’))

for  i  in  range(1,200):

    people_lis.append(People(‘李四’, i ,’女’))

for  i  in  people_lis:

print(i.__dict__)

我的理解:首先,這個東西要先搞明白集合的運行原理,或者說去重原理吧. set(可迭代對象).

1.先說集合的原理吧.集合自帶有相似於for循環的機制,會把放入其中的可迭代對象中的元素依次拿出來用

 自帶的__hash__hsah(元素)的算法,而後在內存中把其保存爲:元素名+指向的形式(指向什麼呢?指向的就

 是存放hash值的格子),當循環到某個元素的時候發現其Hash出來的值對應的格子已經有東西了,這時

 候會生成:(當前元素==已存在的hash值對應的元素名)這樣的一個形式來觸發自帶的__eq__方法,若是這

 兩個比較後的值爲True,則拋棄當前元素不予處理.若是爲Flase,則再次進行一系列運算,從而保證獲得一個

 不一樣的值再予以保存.

2.再來講說這個列子中的變化. 首先給了set一個可迭代的列表,set會利用自帶的循環機制挨個拿出來列表

   中的每一個元素,而後用自帶的hash算法準備給元素進行運算,此時必然是hash(元素)這麼的一個形式,可是這

   種形式在此列中還有另外一層含義,那就是調用對象的hash函數的意思,對象本類此時就具備這個函數,因而

   就走了對象本身的了,然而本身的hash算法是通過修改的,就是提取對象中某一部分來進行hsah運算,不作

 對象總體的運算,運算完成後會在內存中保存成(完整對象名+修改算法後的指向).當下一次循環來的對象

 提取相同部分作完運算,如發現該指向已然有東西了,set準備再次用==來對比當前對象和已存對象值是

 否相同時( 此時形式爲:當前對象==已存對象).這個形式的另外一層意義就起做用了,這是要調set__eq__

 方法,對象本類就有該方法,因而走的就是本類的__eq__方法,可是本類的這個東西也是通過修改的,修改的

 是對比對象中某一段的值是否相同,相同則拋棄不予處理,不一樣則存起來.

 因自帶的__hash__ __eq__的運算標準修改爲了對象中的姓名+性別的形式組成的字符串,因此運算時

 只會運算這個字符串,因此成了姓名和性別相同的去重,而無論其他部分是否相同.

相關文章
相關標籤/搜索