I have a bunch of sorted lists of objects, and a comparison function
class Obj :
def __init__(p) :
self.points = p
def cmp(a, b) :
return a.p
Below is an example of a function that runs in O(n) comparisons.
You could make this faster by making a and b iterators and incrementing them.
I have simply called the function twice to merge 3 lists:
def zip_sorted(a, b):
'''
zips two iterables, assuming they are already sorted
'''
i = 0
j = 0
result = []
while i < len(a) and j < len(b):
if a[i] < b[j]:
result.append(a[i])
i += 1
else:
result.append(b[j])
j += 1
if i < len(a):
result.extend(a[i:])
else:
result.extend(b[j:])
return result
def genSortedList(num,seed):
result = []
for i in range(num):
result.append(i*seed)
return result
if __name__ == '__main__':
a = genSortedList(10000,2.0)
b = genSortedList(6666,3.0)
c = genSortedList(5000,4.0)
d = zip_sorted(zip_sorted(a,b),c)
print d
However, heapq.merge uses a mix of this method and heaping the current elements of all lists, so should perform much better
Python standard library offers a method for it: heapq.merge.
As the documentation says, it is very similar to using itertools (but with more limitations); if you cannot live with those limitations (or if you do not use Python 2.6) you can do something like this:
sorted(itertools.chain(args), cmp)
However, I think it has the same complexity as your own solution, although using iterators should give some quite good optimization and speed increase.
I like Roberto Liffredo's answer. I didn't know about heapq.merge(). Hmmmph.
Here's what the complete solution looks like using Roberto's lead:
class Obj(object):
def __init__(self, p) :
self.points = p
def __cmp__(self, b) :
return cmp(self.points, b.points)
def __str__(self):
return "%d" % self.points
a = [Obj(1), Obj(3), Obj(8)]
b = [Obj(1), Obj(2), Obj(3)]
c = [Obj(100), Obj(300), Obj(800)]
import heapq
sorted = [item for item in heapq.merge(a,b,c)]
for item in sorted:
print item
Or:
for item in heapq.merge(a,b,c):
print item