def align_iterators(func, *iterables):
 class myiter:
  def __init__(self, it):
   self.it = it
   self.key = self.value = None
   self.iternext()
  def iternext(self):
   try:
    self.value = next(self.it)
    self.key = func(self.value)
   except StopIteration:
    self.value = self.key = None
  def __call__(self, key):
   retval = None
   if (key == self.key):
    retval = self.value
    self.iternext()
   elif (self.key and (key > self.key)):
    raise ValueError(u'Iterator has been left behind')
   return retval
 iters = [myiter(it) for it in iterables]
 minvals = minkey = True
 while True:
  minvals = [_f for _f in [it.key for it in iters] if _f]
  if minvals:
   minkey = min(minvals)
   (yield (minkey, [it(minkey) for it in iters]))
  else:
   break

def align_iterators ( func , * iterables ) : class myiter : def __init__ ( self , it ) : self . it = it self . key = self . value = None self . iternext ( ) def iternext ( self ) : try : self . value = next ( self . it ) self . key = func ( self . value ) except StopIteration : self . value = self . key = None def __call__ ( self , key ) : retval = None if ( key == self . key ) : retval = self . value self . iternext ( ) elif ( self . key and ( key > self . key ) ) : raise ValueError ( u'Iterator has been left behind' ) return retval iters = [ myiter ( it ) for it in iterables ] minvals = minkey = True while True : minvals = [ _f for _f in [ it . key for it in iters ] if _f ] if minvals : minkey = min ( minvals ) ( yield ( minkey , [ it ( minkey ) for it in iters ] ) ) else : break
this generator takes a bunch of iterables that are ordered by func it sends out ordered tuples:: (func .