1. 程式人生 > >第027講:集合:在我的世界裡,你就是唯一

第027講:集合:在我的世界裡,你就是唯一

目錄

測試題

0. 請問集合的唯一作用是什麼呢?

1. 如果你希望建立的集合是不變的,應該怎麼做?

2. 請問如何確定一個集合裡邊有多少個元素?

3. 請目測以下程式碼會列印什麼內容?

4. 請問 set1 = {[1, 2]} 和 set1 = set([1, 2]) 執行的結果一樣嗎?

5. 開啟你的IDLE,輸入set1 = {1, 1.0},你發現了什麼?

6. 請問如何給集合新增和刪除元素?

動動手

0. 自學擴充套件:自己花點時間看下這個表格(http://bbs.fishc.com/thread-45276-1-1.html),今後會用上的^_^

1.本節課回顧


測試題

0. 請問集合的唯一作用是什麼呢?

答:集合幾乎所有的作用就是確保裡邊包含的元素的唯一性,就像世界上沒有兩片完全相同的樹葉一樣,集合內不可能存在兩個相同的元素!

1. 如果你希望建立的集合是不變的,應該怎麼做?

答:frozenset()

2. 請問如何確定一個集合裡邊有多少個元素?

答:沒錯,len()函式正好可以滿足你此刻的需求^_^

3. 請目測以下程式碼會列印什麼內容?

>>> num_set = set([1, 2, 3, 4, 5])

>>> num_set[0]

答:會報錯,因為集合是無序的。

4. 請問 set1 = {[1, 2]} 和 set1 = set([1, 2]) 執行的結果一樣嗎?

答:不一樣,set1 = set([1, 2]) 會生成一個集合{1, 2},但set1 = {[1, 2]}卻會報錯。

  1. >>> set1 = {[1, 2]}
  2. Traceback (most recent call last):
  3.   File "<pyshell#17>", line 1, in <module>
  4.     set1 = {[1, 2]}
  5. TypeError: unhashable type: 'list'

從報錯資訊上我們看到“列表不是可雜湊型別”,沒錯,列表是可變的,它怎麼可以雜湊呢?!咦,等等,這句話好像在那聽過……呃,敢情集合跟字典的儲存方式一樣的丫!

其實你再想想就會覺得很有道理,利用雜湊函式計算,相同的元素得到的雜湊值(存放地址)是相同的,所以在集合中所有相同的元素都會覆蓋掉,因此有了集合的唯一性。

然後你繼續接著想就覺得更有道理了,通過雜湊函式計算的地址不可能是按順序排放的,所以集合才強調是無序的!

5. 開啟你的IDLE,輸入set1 = {1, 1.0},你發現了什麼?

答:沒錯, 集合內容是{1.0},其實你弄懂了上一題,這一題一樣容易:因為在Python的雜湊函式會將相同的值的元素計算得到相同的地址,所以1和1.0是等值的^_^

6. 請問如何給集合新增和刪除元素?

答:使用add()方法可以為集合新增元素,使用remove()方法可以刪除集合中已知的元素。

  1. >>> num1.add(6)
  2. >>> num1
  3. {0, 1, 2, 3, 4, 5, 6}
  4. >>> num1.remove(6)
  5. >>> num1
  6. {0, 1, 2, 3, 4, 5}

動動手

0. 自學擴充套件:自己花點時間看下這個表格(http://bbs.fishc.com/thread-45276-1-1.html),今後會用上的^_^

由於集合型別不是我們教學的重點,所以課堂中小甲魚僅強調基本的使用方法,這裡幫大家把Python集合型別的所有內建方法做成一個總結表,以便供大家使用時參考。

集合型別內建方法總結

集合(s).方法名

等價符號

方法說明

s.issubset(t) s <= t 子集測試(允許不嚴格意義上的子集):s 中所有的元素都是 t 的成員
  s < t 子集測試(嚴格意義上):s != t 而且 s 中所有的元素都是 t 的成員
s.issuperset(t) s >= t 超集測試(允許不嚴格意義上的超集):t 中所有的元素都是 s 的成員
  s > t 超集測試(嚴格意義上):s != t 而且 t 中所有的元素都是 s 的成員
s.union(t) s | t 合併操作:s "或" t 中的元素
s.intersection(t) s & t 交集操作:s "與" t 中的元素
s.difference s - t 差分操作:在 s 中存在,在 t 中不存在的元素
s.symmetric_difference(t) s ^ t 對稱差分操作:s "或" t 中的元素,但不是 s 和 t 共有的元素
s.copy()   返回 s 的拷貝(淺複製)

以下方法僅適用於可變集合

   
s.update s |= t 將 t 中的元素新增到 s 中
s.intersection_update(t) s &= t 交集修改操作:s 中僅包括 s 和 t 中共有的成員
s.difference_update(t) s -= t 差修改操作:s 中包括僅屬於 s 但不屬於 t 的成員
s.symmetric_difference_update(t) s ^= t 對稱差分修改操作:s 中包括僅屬於 s 或僅屬於 t 的成員
s.add(obj)   加操作:將 obj 新增到 s
s.remove(obj)   刪除操作:將 obj 從 s 中刪除,如果 s 中不存在 obj,將引發異常
s.discard(obj)   丟棄操作:將 obj 從 s 中刪除,如果 s 中不存在 obj,也沒事兒^_^
s.pop()   彈出操作:移除並返回 s 中的任意一個元素
s.clear()   清除操作:清除 s 中的所有元素

1.本節課回顧

>>> num = {}
>>> type(num)
<class 'dict'>
>>> num2 = {1, 2, 3, 4}
>>> type(num2)
<class 'set'>

大括號並不是字典的特權,在Python裡,如果用大括號括起一堆沒有對映關係的數字時,這一堆數字就是集合。

集合的特點:(唯一)

>>> num = {1, 1, 2, 2, 3, 4}
>>> num
{1, 2, 3, 4}

集合和字典一樣,都是無序的,不支援index。

如何建立一個集合:

一種是直接把一堆元素用大括號括起來

一種是使用工廠函式set()

>>> set1 = set([1, 2, 2, 3, 4])
>>> set1
{1, 2, 3, 4}
>>> set1 = set('I love you')
>>> set1
{'I', 'v', 'e', 'o', 'y', 'u', ' ', 'l'}

搞搞看:去除列表中重複的元素:

[0, 1, 2, 3, 4, 5, 5, 3, 1]

如果沒學習集合,我們會:

>>> num = [0, 1, 2, 3, 4, 5, 5, 3, 1]
>>> temp = []
>>> for each in num:
    if each not in temp:
        temp.append(each)

        
>>> temp
[0, 1, 2, 3, 4, 5]

使用集合,如下:

>>> num = [0, 1, 2, 3, 4, 5, 5, 3, 1]
>>> num = list(set(num))
>>> num
[0, 1, 2, 3, 4, 5]

但是要注意,使用集合得到的是無序的。

如何訪問集合中的值:

可以使用for把集合中的資料一個個讀取出來

可以通過in 和 not in 判斷一個元素是否在集合中已經存在。

內建函式 add() 和 remove()

>>> num = {0, 1, 2, 3, 4, 5}
>>> num.add(6)
>>> num
{0, 1, 2, 3, 4, 5, 6}

>>> num.remove(1)
>>> num
{0, 2, 3, 4, 5, 6}

不可變集合

frozen:冰凍的,凍結的

frozenset() 定義不可變集合

>>> num = frozenset((1, 2, 3, 4, 5))
>>> num
frozenset({1, 2, 3, 4, 5})
>>> num.add(0)
Traceback (most recent call last):
  File "<pyshell#34>", line 1, in <module>
    num.add(0)
AttributeError: 'frozenset' object has no attribute 'add'