示例#1
0
def merge_sorted_lists():
    k = 10
    n = 10
    min_value = 0
    max_value = 30
    sorted_lists = generate_sorted_lists(k,n,min_value,max_value)
    sorted_list = SingleLinkedList()
    heap = MinHeap([], 0)
    # fill in the 1st batch
    for i, l in sorted_lists.items():
        heap.add(IdAndValue(i, l.pop(0)))

    while len(sorted_lists) > 0:
        item = heap.pop()
        sorted_list.append(item.get_value())

        list_id = item.get_id()

        if list_id in sorted_lists:
            value = sorted_lists[list_id].pop(0)
            if len(sorted_lists[list_id]) <= 0:
                sorted_lists.pop(list_id)

            heap.add(IdAndValue(list_id, value))

        else:
            list_id, list = sorted_lists.items()[0]
            heap.add(IdAndValue(list_id, list.pop(0)))

            if len(list) <= 0:
                sorted_lists.pop(list_id)
    while not heap.is_empty():
        sorted_list.append(heap.pop())

    print k*n, len(sorted_list), sorted_list
示例#2
0
def sort_k_sorted(arr, k):
    ans = []
    h = MinHeap()
    for i in range(k + 1):
        h.insert(arr[i])
    for i in range(k + 1, len(arr)):
        smallest = h.extract()
        ans.append(smallest)
        h.insert(arr[i])
    while not h.is_empty():
        smallest = h.extract()
        ans.append(smallest)
    return ans
 def shortest_paths(self, v):
     '''
     Computes the shortest path distances from a source vertex to all other
     vertices using Dijkstra's algorithm.
     '''
     processed = {}  # mapping of processed vertices to geodesic distance
     candidates = {} # mapping of candidate vertices to their Dijkstra scores; exists for convenience of O(1) lookups
     trace = []      # stores edges in order of processing; used to extract shortest paths
     def dijkstra_score(src, dest):
         return processed[src] + self.getWeight(src, dest)
     # Initialize Dijkstra scores
     for n in self.nodes:
         if n == v:
             processed[n] = 0
             for dest in self.edges[n]:
                 score = dijkstra_score(n, dest)
                 if dest not in candidates or score < candidates[dest]:
                     candidates[dest] = score
         else:
             if n not in candidates:
                 candidates[n] = float('inf')
     # heapify node/score tuples, provide comparison key
     unprocessed = MinHeap(list(candidates.items()), lambda x:x[1])
     # compute shortest paths
     while not unprocessed.is_empty():
         n,s = unprocessed.extract_min()
         processed[n] = s
         candidates.pop(n)
         if len(trace) == 0:
             trace.append(Edge(v, n)) # Investigate KeyError when using WeightedEdge
         else:
             src = trace[-1].getDestination()
             trace.append(Edge(src, n)) # Investigate KeyError when using WeightedEdge
         for dest in self.edges[n]:
             if dest in candidates:
                 unprocessed.delete((dest, candidates[dest]))
                 score = dijkstra_score(n, dest)
                 best = min(candidates[dest], score)
                 candidates[dest] = best
                 unprocessed.insert((dest, best))
     return (processed, PathFinder(trace))
class MedianMaintenance:
    def __init__(self):
        self.hlow_heap = MaxHeap()
        self.hhigh_heap = MinHeap()

    def compute_median(self, i):
        self.insert_heap(i)
        self.balance_heap()
        return self.median()

    def balance_heap(self):
        if self.hhigh_heap.size - self.hlow_heap.size > 1 : # rebalance heap to keep it balanced
            high = self.hhigh_heap.extract_min()
            self.hlow_heap.insert(high)
        elif self.hlow_heap.size - self.hhigh_heap.size > 1:
            low = self.hlow_heap.extract_max()
            self.hhigh_heap.insert(low)

    def insert_heap(self, i):
        if self.hlow_heap.is_empty():
            low = None
        else:
            low = self.hlow_heap.peek_max()
        if self.hhigh_heap.is_empty():
            high = None
        else:
            high = self.hhigh_heap.peek_min()
        if low is None or i < low:
            self.hlow_heap.insert(i)
        elif high is not None and i > high:
            self.hhigh_heap.insert(i)
        else:# i wedged inbetween insert in first heap by default
            self.hlow_heap.insert(i)

    def median(self):
        if self.hhigh_heap.size - self.hlow_heap.size == 1:
            return self.hhigh_heap.peek_min()
        else:# default choice when hlow is bigger/same size as hhigh
            return self.hlow_heap.peek_max()
示例#5
0
        g.add_edge(curr, int(j[0]), int(j[1]))

minheap = MinHeap()

start_vertex = 1
#store shortest distances, by default is infinite length to reach
shortest_distance = {start_vertex: 0}
added_vertices = [1]
curr = start_vertex
curr_vertex = g.get_graph()[curr]
for neighbour, weight in curr_vertex.get_neighbours().items():
    #key is the weight of getting to each vertex in the unexplored area
    #first vertex in data is the source and second is the destination
    minheap.insert(weight, curr, neighbour)

while not minheap.is_empty():
    popped = minheap.pop()
    curr = popped.get_data()[1]
    if curr in shortest_distance:
        #just delete and move on since this vertex has already been seen
        continue
    #the vertex from the searched that points to the new element
    curr_parent = popped.get_data()[0]
    #add current vertex to shortest distance so the distance has been set
    shortest_distance[curr] = popped.get_key()
    for neighbour, weight in g.graph[curr].get_neighbours().items():
        #popping from min heap and ignoring those that were seen before, so the shortest paths will keep coming up first, so no need to delete
        #the check if curr in shortest distance also ensures that our duplicate entries for same vertex will be ignored since they would
        #have previously been inserted into minheap

        #for below, new distance to each neighbour from the current would be the shortest distance to current + weight of edge between them