python進階(資料結構和演算法[二])

來源:互聯網
上載者:User

標籤:

找到最大或者最小的N個元素

heapq模組有兩個函數–nlargest()nsmallest()正好能解決我們的問題。

>>> print(heapq.nlargest(3, nums))[43, 23, 8]>>> print(heapq.nsmallest(3,nums))[-1, 1, 2]#anotherimport heapqportfolio = [   {‘name‘: ‘IBM‘, ‘shares‘: 100, ‘price‘: 91.1},   {‘name‘: ‘AAPL‘, ‘shares‘: 50, ‘price‘: 543.22},   {‘name‘: ‘FB‘, ‘shares‘: 200, ‘price‘: 21.09},   {‘name‘: ‘HPQ‘, ‘shares‘: 35, ‘price‘: 31.75},   {‘name‘: ‘YHOO‘, ‘shares‘: 45, ‘price‘: 16.35},   {‘name‘: ‘ACME‘, ‘shares‘: 75, ‘price‘: 115.65}]cheap = heapq.nsmallest(3, portfolio, key=lambda s: s[‘price‘])expensive = heapq.nlargest(3, portfolio, key=lambda s: s[‘price‘])print(cheap)print(expensive)# 輸出[{‘shares‘: 45, ‘name‘: ‘YHOO‘, ‘price‘: 16.35}, {‘shares‘: 200, ‘name‘: ‘FB‘, ‘price‘: 21.09}, {‘shares‘: 35, ‘name‘: ‘HPQ‘, ‘price‘: 31.75}][{‘shares‘: 50, ‘name‘: ‘AAPL‘, ‘price‘: 543.22}, {‘shares‘: 75, ‘name‘: ‘ACME‘, ‘price‘: 115.65}, {‘shares‘: 100, ‘name‘: ‘IBM‘, ‘price‘: 91.1}]

簡單的介紹一下heapq中的方法:

import heapq#heapq.heappush(heap,item)  #heap為定義堆,item 增加的元素;#eg.  heap=[]  heapq.heappush(heap, 2) # heap = [2]#heapq.heapify(list)        #將列錶轉換為堆#eg.   list=[5,8,0,3,6,7,9,1,4,2]   heapq.heapify(list) #heapq.heappop(heap)        #刪除最小的值#eg.  heap=[2, 4, 3, 5, 7, 8, 9, 6]  heapq.heappop(heap) ---->heap=[3, 4, 5, 7, 9, 6, 8]#heapq.heapreplace(heap, item)     #刪除最小元素值,添加新的元素值#eg.  heap=[2, 4, 3, 5, 7, 8, 9, 6]  heapq.heapreplace(heap, 11) ------>heap=[2, 3, 4, 6, 8, 5, 7, 9, 11]#heapq.heappushpop(heap, item)     #首判斷添加元素值與堆的第一個元素值對比,如果大於則刪除最小元素,然後添加新的元素值,否則不更改堆#eg.   條件:item >heap[0]   heap=[2, 4, 3, 5, 7, 8, 9, 6]   heapq.heappushpop(heap, 9)---->heap=[3, 4, 5, 6, 8, 9, 9, 7]   條件:item   heap=[2, 4, 3, 5, 7, 8, 9, 6]   heapq.heappushpop(heap, 9)---->heap=[2, 4, 3, 5, 7, 8, 9, 6]#heapq.merge(...)             #將多個堆合并#heapq.nlargest (n, heap)     #查詢堆中的最大元素,n表示查詢元素個數#eg.  heap=[2, 3, 5, 6, 4, 8, 7, 9]  heapq.nlargest (1, heap)--->[9]#heapq.nsmallest(n, heap)     #查詢堆中的最小元素,n表示查詢元素個數#eg. heap=[2, 3, 5, 6, 4, 8, 7, 9] heapq.nlargest (1, heap)--->[2]
對不一樣的資料排序使用不同的方式
  1. 當要尋找的元素相對較少時,nlargestnsmallest是最合適的。
  2. 只是想找到最大最小元素,使用minmax是最合適的。
  3. 如果N和集合本身相差不大,使用排序並切片的方式是合適的(sorted(items)[:N]sorted(items)[-N:])。
  4. N相對總元素較少的時候,適合使用將資料轉化成列表,元素順序以堆的順序排列(參照上述的heapq.heapify())。
實現優先順序隊列
import heapq # 堆的資料結構,通過對數時間能找到最大或最小元素class PriorityQueue:    def __init__(self):        self._queue = [] #初始化的列表        self._index = 0 # 初始化的索引,用去比較優先順序相同的元素    def push(self, item, priority):        # 通過heappush向_queue列表中添加一個元素(元組),預設是小頂堆,因此將優先順序取反;        # 元組比較大小是逐項的,因此添加_index作為相同優先順序比較的第二個比較項;永遠不會比較第三項        heapq.heappush(self._queue, (-priority, self._index, item))        self._index += 1    def pop(self):        return heapq.heappop(self._queue)[-1] #彈出的是三元組(-priority, _index, Item(‘‘),只顯示最後一項即可#構造的元素類class Item:    def __init__(self, name):        self.name = name    def __repr__(self):        return ‘Item({!r})‘.format(self.name)q = PriorityQueue()q.push(Item(‘foo‘), 1)q.push(Item(‘bar‘), 5)q.push(Item(‘barm‘), 4)q.push(Item(‘grok‘), 1)print(q.pop())print(q.pop())print(q.pop())print(q.pop())

輸出:

Item(‘bar‘)Item(‘barm‘)Item(‘foo‘)Item(‘grok‘)

從輸出中我們看出:是按照優先順序輸出,相同優先順序的按照索引較小的先輸出(因為是小頂堆並且先插入的索引值較小)

python進階(資料結構和演算法[二])

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.