1. 程式人生 > 實用技巧 >內建函式之 sorted filter map zip

內建函式之 sorted filter map zip

內建函式

sorted

sorted(iterable,*,key=None,reverse=False)
返回一個 新已排序的列表
key 指定帶有單個引數的函式,用於從 iterable 的每個元素中提取用於比較的鍵 (例如 key=str.lower)。 預設值為 None (直接比較元素)
reverse 為一個布林值。 如果設為 True,則每個列表元素將按反向順序比較進行排序。

基本排序
>>>sorted({0: 0, 3: 1, 5: 2, 9: 3, 2: 4})
[0, 2, 3, 5, 9]

如果iterable 是字典,則預設以key進行排序

關鍵函式

key 形參的值應該是一個函式,它接受一個引數並並返回一個用於排序的鍵。這種技巧速度很快,因為對於每個輸入記錄只會呼叫一次 key 函式。

>>>students_tuples = [('john', 'A', 15),('jane', 'B', 12),('dave', 'B', 10),]
>>>sorted(students_tuples,key=lambda x:x[2],reverse=True)   #key為一個lambda函式,迭代接收iterable中的元素作為實參傳給形參x,lambda函式返回x[2]值用於排序
[('john', 'A', 15), ('jane', 'B', 12), ('dave', 'B', 10)] 

對於類物件,也可以使用物件的屬性作為key的返回值

operator函式模組
>>>from operator import itemgetter,attrgetter
>>>sorted(students_tuples,key=itemgetter(2))
[('dave', 'B', 10), ('jane', 'B', 12), ('john', 'A', 15)]

key = itemgetter(2) 等同於 key = lambda x:x[2] ,更簡單、快捷
Operator 模組功能允許多級排序。例如,先根據索引位1,再根據索引位2
>>>sorted(students_tuples,key=itemgetter(1,2))
[('john', 'A', 15), ('dave', 'B', 10), ('jane', 'B', 12)] #先做A、B排序,再在B的基礎上做int排序

filter

filter(function, iterable),返回一個新的迭代器
函式 function 用 iterable 中的元素遍歷,function 返回真的那些元素,構建一個新的迭代器

>>>list(filter(lambda x : x % 3 ==0,range(10)))  #lambda函式用range(10)中的元素作為引數遍歷,取餘為零函式返回值為True,則filter返回這些元素的迭代器
[0, 3, 6, 9]  

如果 function 是 None ,則會假設它是一個身份函式,即 iterable 中所有返回假的元素會被移除。
>>>list(filter(None,range(5)))
[1, 2, 3, 4]

map

map(function, iterable, ...)
返回一個將 function 應用於 iterable 中每一項並輸出其結果的迭代器

>>>dict(map(lambda x:(str(x+1),x+1),range(5))) #lambda函式對iterable重新構造,並返回一個迭代器  
{'1': 1, '2': 2, '3': 3, '4': 4, '5': 5}

如果傳入了額外的 iterable 引數,function 必須接受相同個數的實參並被應用於從所有可迭代物件中並行獲取的項

>>>list(map(lambda x,y:(x+1,y+1),range(5),range(5)))
[(1, 1), (2, 2), (3, 3), (4, 4), (5, 5)]

當有多個可迭代物件時,最短的可迭代物件耗盡則整個迭代就將結束

>>>list(map(lambda x,y:(x+1,y+1),range(5),range(10)))
[(1, 1), (2, 2), (3, 3), (4, 4), (5, 5)]

zip

zip(*iterables)
建立一個聚合了來自每個可迭代物件中的元素的迭代器

>>>list(zip(range(10),range(10),range(10)))
[(0, 0, 0), (1, 1, 1), (2, 2, 2), (3, 3, 3), (4, 4, 4), (5, 5, 5), (6, 6, 6), (7, 7, 7), (8, 8, 8), (9, 9, 9)]

zip與map結合使用生成一個字典

>>>dict(zip(map(lambda x : str(x+1),range(10)),range(10)))
>>>{str(x+1):y for x,y in zip(range(10),range(10))}
{'1': 0, '2': 1, '3': 2, '4': 3, '5': 4, '6': 5, '7': 6, '8': 7, '9': 8, '10': 9}