從5個(gè)維度總結(jié)Python數(shù)據(jù)結(jié)構(gòu)的關(guān)系,發(fā)現(xiàn)了這些技巧
在python中,我們經(jīng)常用列表,字典等數(shù)據(jù)類型進(jìn)行數(shù)據(jù)存儲(chǔ)或者重新構(gòu)造一個(gè)序列,同時(shí)它們之間也有著一些關(guān)聯(lián)關(guān)系,接下來(lái)我們就對(duì)python中常用的幾種數(shù)據(jù)類型進(jìn)行一個(gè)整體性的梳理。

區(qū)別
相同點(diǎn)
- 都相當(dāng)于一個(gè)容器,有存放數(shù)據(jù)的功能
- 都可以用for ... in 進(jìn)行循環(huán)
不同點(diǎn)
- 序列存放的是不同類型的數(shù)據(jù),迭代器中存放的是算法。
- 序列是將數(shù)據(jù)提前存放好,獲取數(shù)據(jù)時(shí)通過(guò)循環(huán)或索引來(lái)取數(shù)據(jù) ;而迭代器不需要存放數(shù)據(jù),獲取數(shù)據(jù)時(shí)通過(guò)算法獲取下一個(gè)數(shù)據(jù) 。
- 序列中的每一個(gè)數(shù)據(jù)都要開辟內(nèi)存空間;而迭代器并不需要,它每次只需要通過(guò)算法計(jì)算出下一個(gè)值即可。從這個(gè)角度來(lái)看,如果進(jìn)行大數(shù)據(jù)量處理,使用迭代器更合適 。
- 序列可以通過(guò)索引或鍵名來(lái)獲取某一個(gè)值,而迭代器只能使用next()獲取下一個(gè)值。
變化趨勢(shì)

從左到右,可以試圖找一些規(guī)律 。
- 從對(duì)數(shù)據(jù)的排序來(lái)看,從左到右可以看出是無(wú)序的,有序的,有規(guī)則(也可以定義成有序的)
- 從對(duì)數(shù)據(jù)的操作靈活度來(lái)看,左邊的操作性更加靈活,可以進(jìn)行增刪改查 ;右邊相對(duì)來(lái)說(shuō)比較單一只能進(jìn)行查詢 (注意:定義后的字符串就只能進(jìn)行查詢,通過(guò)方法生成的字符串并不是原來(lái)的字符串了)。若想關(guān)注這些數(shù)據(jù)類型中的具體方法,可參考:python的5種數(shù)據(jù)結(jié)構(gòu),方法很多記不住嗎?全在這里了.
- 從定義數(shù)據(jù)類型的符號(hào)來(lái)看,也是遵循漢字的大-中-小-引 來(lái)實(shí)現(xiàn)的,如字典|集合是大括號(hào),列表是中括號(hào),元組是小括號(hào),字符串為雙引號(hào)或單引號(hào)。
數(shù)據(jù)類型間的相互轉(zhuǎn)化
以上不同的數(shù)據(jù)類型,也可以實(shí)現(xiàn)兩者之間的相互轉(zhuǎn)化,轉(zhuǎn)化時(shí)只需要通過(guò)調(diào)用對(duì)應(yīng)函數(shù)即可,如下圖

下圖是每種數(shù)據(jù)類型間的相互轉(zhuǎn)化及具體實(shí)例。

通過(guò)以上的表格可以看出,數(shù)據(jù)類型可以進(jìn)行相互轉(zhuǎn)化,總結(jié)有以下幾點(diǎn):
- 無(wú)論轉(zhuǎn)化為什么數(shù)據(jù)類型,都是通過(guò)關(guān)鍵字將具體的數(shù)據(jù)類型括起來(lái),如元組轉(zhuǎn)化為列表:list(tuple)
- 轉(zhuǎn)化為字典時(shí)需要注意的是,必須每?jī)蓚€(gè)數(shù)據(jù)為一組,用括號(hào)括起來(lái),這樣才能正確的生成字典的鍵值對(duì),如果是一個(gè)元素轉(zhuǎn)化時(shí)會(huì)報(bào)錯(cuò) 。
- 轉(zhuǎn)化為字符串時(shí)需要注意的是,雖然通過(guò)str(data)可以轉(zhuǎn)化為字符串,但很多情況并非是我們想要的,我們更想要的是將序列中的元素組合起來(lái)變成一個(gè)字符串 ,如果想實(shí)現(xiàn)這樣的需求,就可以使用join()方法實(shí)現(xiàn)。
轉(zhuǎn)化為字典時(shí)必須要求是兩個(gè)元素組合成一個(gè)元組才能進(jìn)行轉(zhuǎn)化 。那為了簡(jiǎn)便我們可以使用zip()將兩個(gè)序列組成一個(gè)新的字典更加方便。
- # 通過(guò)zip將兩個(gè)列表合并為一個(gè)序列,然后再轉(zhuǎn)化為字典。
- lst1 = ['x','y','z'] #可以是一個(gè)列表,元組,集合
- lst2 = [123,234,345]
- print(dict(zip(lst1,lst2)))
- #輸出:
- {'x': 345, 'y': 234, 'z': 123}
通過(guò)str()進(jìn)行轉(zhuǎn)化后的數(shù)據(jù)雖然變成了字符串,但是我們更想的是把序列中的元素結(jié)合起來(lái)變?yōu)樽址?。那么可以通過(guò)join()方法將其內(nèi)的元素變?yōu)橄胍淖址?/p>
- #語(yǔ)法:
- "sep".join(seq)
- #實(shí)例:
- x = "".join({'a':123,'b':345})
- print("x:",x)
- y = ",".join(['java','python','c++'])
- print("y:",y)
- z = "_".join(("tuple","demo","01"))
- #輸出:
- x: ab
- y: java,python,c++
- z: tuple_demo_01
- #說(shuō)明:
- sep為分隔符,seq序列
便捷式寫法-推導(dǎo)式
在以上的數(shù)據(jù)結(jié)構(gòu)中,部分?jǐn)?shù)據(jù)類型同樣支持推導(dǎo)式,推導(dǎo)式是可以將一個(gè)可迭代對(duì)象構(gòu)建成新的可迭代對(duì)象的表達(dá)式結(jié)構(gòu)體 。通過(guò)推導(dǎo)式可以快速實(shí)現(xiàn)出一個(gè)新的序列或生成器 ,也可以讓代碼更加優(yōu)雅和快捷 。
為了更加直觀,我們可以一張圖來(lái)總結(jié)不同數(shù)據(jù)類型所支持的推導(dǎo)式。我們只需要記住推導(dǎo)式的433.

字典推導(dǎo)式
- #語(yǔ)法:
- {<operation_key:operation_value> for key,value in dict condition }
- #實(shí)例:
- d = {'chinese': 88, 'math': 92, 'english': 93, 'history': 84}
- print("成績(jī)大于90分的科目:", {k: '優(yōu)秀' for k, v in d.items() if v >= 90})
- #輸出
- 成績(jī)大于90分的科目: {'math': '優(yōu)秀', 'english': '優(yōu)秀'}
- #說(shuō)明:
- for循環(huán)后的表達(dá)式可以是條件表達(dá)式或者循環(huán)表達(dá)式,主要是進(jìn)行篩選或嵌套循環(huán)
- 返回結(jié)果是一個(gè)根據(jù)表達(dá)式運(yùn)算后生成出來(lái)的新字典 。
集合推導(dǎo)式:
- #語(yǔ)法:
- {<operation_key:x> for x in set condition }
- #實(shí)例
- s = {x**2 for x in [1, 2, 3]}
- print("集合s:",s)
- #輸出:
- 集合s: {1, 4, 9}
列表推導(dǎo)式
- #語(yǔ)法:
- [ operation(x) for x in list condition ]
- #實(shí)例
- print([random.randint(1,10)+x for x in range(0,10) if x % 2 == 0])
- #結(jié)果:
- [3, 3, 14, 15, 12]
- #說(shuō)明:
- #對(duì)列表推導(dǎo)式常使用的幾種用法
- 用法1:[x for x in iterable ] #循環(huán)后直接打印
- 用法2:[x for x in iterable if condition(x) ] #對(duì)x的條件判斷
- 用法3:[operation(x) for x iterable if condition(x)] #對(duì)x條件判斷后,再對(duì)x進(jìn)行運(yùn)算
- 用法4: [operation(x,y) for x in iterable for y in iterable1] #嵌套循環(huán),對(duì)x,y進(jìn)行運(yùn)算
生成器推導(dǎo)式
- #語(yǔ)法:
- ( operation(x) for x in iterable condition )
- #實(shí)例
- print((random.randint(1,10)+x for x in range(0,10) if x % 2 == 0))
- #結(jié)果:
- <generator object <genexpr> at 0x02FDC420>
- #說(shuō)明:
- 新生成的生成器可以使用for循環(huán),也可以next()獲取其下一個(gè)值
組合用法
以上數(shù)據(jù)結(jié)構(gòu)除了可以作為容器使用,也可以它們結(jié)合起來(lái)使用,以用作其它用途 。比如可以用作條件語(yǔ)句。為了直觀,我們先寫一個(gè)簡(jiǎn)單的if語(yǔ)句。
- score = 92
- if score >= 90:
- print('優(yōu)秀')
- else:
- print('良好')
- #輸出:優(yōu)秀
接下來(lái),我們就通過(guò)以下這三種方式來(lái)重新定義條件語(yǔ)句。

第一種,使用()+[]來(lái)實(shí)現(xiàn)條件判斷
- #語(yǔ)法:
- (<return_false>, <return_true>)[condition_expression]
- #實(shí)例:
- score = 92
- print(('良好','優(yōu)秀')[ score >= 90 ])
- #結(jié)果:
- 優(yōu)秀
- #說(shuō)明:
- 在[]中寫條件語(yǔ)句,在()中寫返回為真和返回為假的值。一定要注意順序,()在前,[]在后
第二種,使用{}+[]來(lái)實(shí)現(xiàn)條件判斷
- #語(yǔ)法:
- {True: <return_true>, False: <return_false>}[<condition_expression>]
- #實(shí)例:
- score = 92
- print({True:'優(yōu)秀',False:'良好'}[ score >= 90 ])
- #結(jié)果:
- 優(yōu)秀
- #說(shuō)明:
- 在[]中寫條件語(yǔ)句,在()中寫返回為真和返回為假的值,一定要注意順序
第三種,對(duì)字符串進(jìn)行條件判斷 ,需要用到eval方法。
- #語(yǔ)法:
- eval("字符串判斷語(yǔ)句")
- #實(shí)例
- print('優(yōu)秀' if eval("score >= 90") else '良好')
- #結(jié)果
- 優(yōu)秀