2016-03-24 27 views
2

Farklı boyutta iki listeden yineleme yapmak istiyorum, ancak aynı hızda değil (yalnızca paralel yineleme için yanıtlar buldum). Örneğin, aynı tür elementleri içeren iki sıralı liste düşünün ve iki listenin ortak geçişini kullanarak, sadece bir listede veya her iki listede yer alan unsurlara göre elemanlar üzerinde bir şeyler yapmak istiyorum.Farklı boyutta iki liste üzerinde yineleme yaparken StopIteration istisnası ile anlaşma

Endeksleri kullanarak bunu nasıl yapacağımı bilirim, ancak yineleyicilerle bunu doğru şekilde yapmanın bir yolu var mı?

StopIteration yükseltilir
list1=[...] 
list2=[...] 

it1=iter(list1) 
it2=iter(list2) 
try: 
    while True: 
     e1=it1.next() 
     e2=it2.next() 

     while compare(e1,e2): 
      doSomething1(e1) 
      e1=it1.next() 

     while compare(e2,e1): 
      doSomething2(e2) 
      e2=it2.next() 

     doSomething3(e1,e2) 
except StopIteration: 
    pass 

# do something with the rest of the list that is at end 

, ben sonunda hangi liste bilmiyorum ve ben kalan öğelerine erişmek için nasıl bilmiyorum: (sonraki çağırarak

Ben çizgisinde bir şey var) istisna kontrol etmek için beni daha uzun listede bir elementi atlatacak, doğrudan e1 veya e2'ye erişerek daha kısa listenin son elemanına ikinci kez erişebileceğim.

Sana, yukarıda ... her (bir sonraki) ancak tüm fikirlerimi sadece kullanan endekslerin daha karmaşık görünüyor çevresi hariç/denemek olması gibi, basit bir kod çalışma Örneğin

bazı çözümleri tahmin edebilirsiniz

def compare(e1,e2):  return e1<e2 
def doSomething1(e1): print "list1: %d"%e1 
def doSomething2(e1): print "list2: %d"%e1 
def doSomething3(e1,e2): print "common: %d"%e1 

list1=[1,2,5,6,8,10,23,56] 
list2=[3,4,5,10] 
+0

Listelerde normalde "Hiçbiri" değeri yoksa, diğer listenin uzunluğuyla eşleştirmek için daha kısa listeyi "Yok" ile doldurabilirsiniz. – Selcuk

+0

Bunun yardımcı olacağını sanmıyorum çünkü iki yineleyicimin paralel olarak ilerlemesini istemiyorum. – romaric

cevap

1

yineleyicileri olabilir yineleme elemanları kalan (tahmin edilen) sayısı döner bir __length_hint__ sahiptir. Bunun doğruluğu yineleyicinizin türüne bağlıdır ve CPython dışı uygulamalarda çalışacağını garanti edemem.

x = [1,2,3,4,5] 
y = iter(x) 
print y.__length_hint__() # prints 5 
print y.next # prints 1 
... 

StopIteration catch'unuzda, hangi yineleyici üyelerinin kaldığını kontrol edebilir ve buna göre hareket edebilirsiniz.

list1=[...] 
list2=[...] 

it1=iter(list1) 
it2=iter(list2) 
try: 
    while True: 
     e1=it1.next() 
     e2=it2.next() 

     while compare(e1,e2): 
      doSomething1(e1) 
      e1=it1.next() 

     while compare(e2,e1): 
      doSomething2(e2) 
      e2=it2.next() 

     doSomething3(e1,e2) 
except StopIteration: 
    if it1.__length_hint__() > 0: 
     #handle unhandled list1 items. 
    elif it2.__length_hint__() > 0: 
     #handle unhandled list2 items. 
    else: 
     #both lists have been exhausted. 
+1

Bilgi için teşekkürler, benim için çalışıyor. Python 3.4'ten (https://docs.python.org/dev/library/operator.html#operator.length_hint) beri bir operator.length_hint() işlevinin olduğunu gördüm. – romaric