Python Data Structure Learning notes (ix)

Source: Internet
Author: User

    • Priority Queues
      • 9.1 ADT
      • 9.2 Implementing a priority queue
        • Use unordered list to implement
        • Use an ordered list to implement a priority queue
      • 9.3 Heaps
        • Heap data structure
        • Using heaps to implement priority queues
        • A complete binary tree based on array implementation
        • Use the minimum priority queue to sort
      • Adaptable Priority queue
        • Locators
Priority Queues9.1 ADT
    • P.add (k, v)
    • P.min (): Return (K, V)
    • P.remove_min (): Return (K,V)
    • P.is_empty ()
    • Len (P)

The priority queue may have several elements with the same key value and are all minimal, when the smallest value is one of the randomly selected ones.

9.2 Implementing a priority queue
Class Priorityqueuebase: "" "    abstract base class for a priority queue.        " " Class _item: "" "        lightweight composite to store priority queue items.        " " __slots__ = ' _key ', ' _value '                def __init__ (self, k, v):            self._key = k            Self._value = v                    def __lt__ (self, othe R):            return Self._key < Other._key    def is_empty (self):        return len (self) = = 0

In the abstract base class of the priority queue, define a simple _item class to implement the storage of (k, V) pairs

Use unordered list to implement

For the storage of the list in the priority queue, one way is to select the previous positionallist, this method because the elements inside the queue do not need to keep order, add an element only need O (1) time to complete, but for Min, remove_ The min operation will need to traverse the entire list to find the smallest element's position, so it needs O (n) time.

Class Unsortedpriorityqueue (Priorityqueuebase):    def _find_min (self): "" "        return Position of the item with min key" " "        if Self.is_empty ():            Raise Empty (' Priority queue is empty ')        small = Self._data.first ()        walk = self._ Data.after (small) while walf are not        None:            if Walf.element () < Small.element ():                small = walk            walk = Sel F._data.after (walk)        return small    def __init__ (self):        Self._data = Positionallist ()    def __len__ ( Self):        return len (self._data)    def add (self, key, value):        self._data.add_last (Self._item (key, value))    def min (self):        p = self._find_min ()        item = p.element ()        return (Item._key, item._value)    def Remove_min (self): "" "        Remove and return (K, v) a tuple with min key.        " " p = self._find_min ()        item = Self._data.delete (P)        return (Item._key, Item._value)
Use an ordered list to implement a priority queue

The

is implemented by using an ordered list of elements that are the smallest element in the queue.

Class Sortedpriorityqueue (Priorityqueuebase): "" "a min priority queue implemented with a sorted list" "" Def __i Nit__ (self): Self._data = Positionallist () def __len__ (self): return Len (self._data) def add (self, key        , value): "" "Add a Key-value Pair" "" Newest = Self._item (key, value) walk = Self._data.last ()  While walk isn't none and newest < Walk.element (): Walk = Self._data.before (walk) If Walk is None: # new key is smallest self.= _data.add_first (newest) else:self._data.add_after (Walk, Newset ) def min (self): "" "return (k, v) of tuple with min key" "" If Self.is_empty (): Raise Empty ('    Priority queue is empty ') P = self._data.first () item = P.element () return (Item._key, Item._value) def remove_min (self): "" "Remove and return (K, v) a tuple with min key" "" If Self.is_empty (): RA Ise Empty (' Priority QueuE is empty ') item = Self._data.delete (Self._data.first ()) return (Item._key, Item._value) 
9.3 Heaps

The preceding priority queues implemented using ordered and unordered queues each have advantages. Using an unordered queue can reach O (1) at the time of insertion, but the time to find the smallest element will be O (n). An ordered queue implements an O (n) time to insert, but only O (1) is required to find the smallest element.

Now introduced a new data structure, binary heap, can be in the logarithmic time complex implementation of inserting and finding operations.

Heap data structure

The elements in the binary heap meet the following properties:

    • For each position that is not the root p, the location stores a key greater than or equal to the key stored on its parent node, so that the path from the root node down to the

All keys are not reduced, so the root node key is the smallest.

    • Full Binary Tree properties: A heap of H is a height of t if the number of layers 0 to H-1 is full, and in layer H can be dissatisfied, but nodes from left to right

Tightly arranged, and there is no gap on the left, it can be said that it is complete.

    • A complete two-fork heap, when there are n elements in it, its height h does not exceed Logn
Using heaps to implement priority queues

Because the heap height does not exceed the logarithm of n, if we implement the updated operation this height, then we can achieve the complexity of not exceeding the logarithmic time.

For the implementation of using the heap, we need to be concerned with inserting a new element and how to do it. To maintain the tree's complete nature, this new node should be on the right of the last node in the bottom layer, if the layer is just full, then the first node in the new layer. This only satisfies the tree's complete nature, but it also considers that the key value of a node is not less than the key of its parent node. Assuming that the new node is p, his parent node is Q, and if KP < KQ, then the two nodes need to be exchanged. The P-node may still be smaller than its new parent node after the swap, then continue checking to see if it is going to be swapped until the P-node is pushed to the root node or has satisfied the nature. Because the worst case of the insert operation is to push the new node to the root node position, the time complexity is O (LOGN)

Now to remove_min the realization. To ensure the complete nature of the tree, you can first swap the root node with the rightmost node in the bottom layer, and then delete the node at the bottom right. This is possible to destroy the child node key is not less than the nature of the parent node. The method of maintenance is similar to insertion, starting at the root node, and comparing it to the key of its child nodes, noting that it may have 2 sub-nodes, so it needs to be compared with the smaller of the key. If the root's key value is greater than the key value of the child node, it is exchanged and then continues to determine if further swapping is required. The worst case is also the complexity of O (Logn).

A complete binary tree based on array implementation

F (P) is the subscript that the position p stores in the array

    • If p is the root, then f (p) = 0
    • If P is the left child of position Q, then f (p) = 2f (q) + 1
    • If P is the right child of position Q, then f (p) = 2f (q) + 2

One benefit of using an array implementation is that it is convenient to find the lowest-right node of the lower level, which is where the subscript n-1 is stored.

Class Heappriorityqueue (Priorityqueuebase): "" "a min-oriented priority queue implemented with a binary heap." " Def _parent (Self, j): Return (J-1)//2 def _left (self, j): Return 2 * j + 1 def _ri            Ght (Self, j): Return 2 * j + 2 def _has_left (self, j): Return Self._left (J) < Len (self._data)  def _has_right (Self, j): Return Self._right (J) < Len (self._data) def _swap (self, I, j): "" "Swap The elements at indices i and J of Array "" "self._data[i], self._data[j] = Self._data[j], self._data[i] def _up Heap (Self, j): Parent = Self._parent (j) If J > 0 and Self._data[j] < Self._data[parent]: SE Lf._swap (j, parent) Self._upheap (parent) # Recur at position of the parent Def _downheap (Self, j): If SE                Lf._has_left (j): Left = Self._left (j) Small_child = Left if Self._has_right (j): right = Self._right (j)                If self._data[right] < Self._data[left]: Small_child = right If Self._dat A[small_child] < Self._data[j]: Self._swap (J, Small_child) Self._downheap (small_child) #-        ---------------Public Methods--------------------def __init__ (self): Self._data = [] def __len__ (self): Return Len (self._data) def add (self, key, value): Self._data.append (Self._item (key, value)) . _upheap (Len (self._data)-1) def min (self): if Self.is_empty (): Raise empty (' priority queue ' is empty            ') item = self._data[0] Return (Item._key, item._value) def remove_min (self): if Self.is_empty ():         Raise empty (' Priority queue is Empty ') self._swap (0, Len (self._data)-1) item = Self._data.pop ()         Self._downheap (0) return (Item._key, Item._value)
Use the minimum priority queue to sort

You can construct an empty priority queue, then insert the elements you want to sort into the queue, and then remove_min get an ordered queue by constantly extracting elements from the queue.

Adaptable Priority queue

The priority queue can now be implemented to remove the smallest element, but there may be some problems that need to be addressed, such as some of the customers in the queue who suddenly say they do not want to go ahead and need to be able to remove any element. There are a number of people in line, such as the priority in the back, but suddenly took out a VIP card, then his priority has suddenly become very high, need to be able to change his key to a new value.

To support these new operations, we need to define a new ADT adaptable priority queue .

Locators

To modify any of the elements in the queue, we need to be able to navigate to any element inside. Now add the locator locators, and when adding a new element to the queue, return a locator to the parent function.

    • P.update (Loc, K, V): A key that specifies the location of Loc, and value is updated.
    • P.remove (Loc): Deletes the specified element and returns (key, value)
Class Adaptableheappriorityqueue (Heappriorityqueue): "" "a locator-based priority queue implemented with a binary heap.            "" "Class Locator (Heappriorityqueue._item): __slots__ = ' _index ' def __init__ (self, k, V, j): Super (). __init__ (k, v) self._index = J #--------------nonpublic methods-----------------# ove        Rride swap to record new indices def _swap (self, I, J): Super (). _swap (i, j) Self._data[i]._index = i Self._data[j]._index = J def _bubble (Self, j): "" To move an element up or down to the appropriate position "" "if J > 0 and Self._data[j] & Lt Self._data[self._parent (j)]: Self._upheap (j) Else:self._downheap (j) def add (self, key, VA        Lue): "" "Add a Key-value pair." " token = self. Locator (key, value, Len (self._data)) Self._data.append (token) self._upheap (len (self._data)-1) retur N Token def update (self, loc, Newkey, newval): j = Loc._index IF Not (0 <= J < len (self) and self._data[j] is loc): Raise ValueError (' invalid locator ') Loc._key = Newkey Loc._value = newval Self._bubble (j) def remove (self, loc): "" "Remove and return (key , value) "" "J = Loc._index If not (0 <= J < len (self) and self._data[j] is loc): Raise Val Ueerror (' invalid locator ') if j = Len (self)-1: # Remove the last position Self._data.pop () El Se:self._swap (J, Len (self)-1) Self._data.pop () self._bubble (j) Return (Loc._key , Loc._value)

Python Data Structure learning Note (ix)

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

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.