जनरेटर के माध्यम से लूप कैसे करें


81

एक जनरेटर के माध्यम से एक लूप कैसे हो सकता है? मैंने इस तरह से सोचा:

gen = function_that_returns_a_generator(param1, param2)
if gen: # in case the generator is null
    while True:
        try:
            print gen.next()
        except StopIteration:
            break

क्या अधिक पाइथोनिक तरीका है?


मैं उपयोग करने का सुझाव दूंगा break; नहींcontinue
जॉन क्लेमेंट्स

मैं वास्तव में इसे इस तरह से करूंगा, जहां जनरेटर किसी तत्व पर अपवाद फेंक सकता है, लेकिन आप पुनरावृत्ति को रोकना नहीं चाहते हैं।
लूटेब्रिट

जवाबों:


145

केवल

for x in gen:
    # whatever

चाल चलेगा। ध्यान दें कि if genहमेशा रिटर्न True


6
नहीं, if genहमेशा नहीं लौटता True। यदि ऑप्स function_that_returns_a_generator()रिटर्न None, बयान में genमूल्यांकन करता है । Falseif
ड्रेविको

44
@drevicko: मैं मान रहा था कि function_that_returns_a_generator()एक जेनरेटर लौटाता है (बोल्ड धारणा, है ना?)। Noneजेनरेटर नहीं है।
स्वेन मार्नाच

चूंकि, ओपी "पाइथोनिक तरीका" के लिए पूछता है, इसलिए यह उत्तर काफी वैध लगता है, यह देखते हुए कि पायथन ईएएफपी ;-) की वकालत करता है
DerMike

17
for item in function_that_returns_a_generator(param1, param2):
    print item

आपको यह देखने के लिए परीक्षण के बारे में चिंता करने की ज़रूरत नहीं है कि क्या आपके फ़ंक्शन द्वारा कुछ भी लौटाया जा रहा है जैसे कि वहाँ कुछ भी नहीं लौटा है जो आप लूप में प्रवेश नहीं करेंगे।


9

मामले में आपको जनरेटर के उत्पादन की आवश्यकता नहीं है क्योंकि आप केवल इसके दुष्प्रभावों के बारे में परवाह करते हैं, आप निम्नलिखित एक-लाइनर का उपयोग कर सकते हैं:

for _ in gen: pass

3
या बसlist(gen)
15

7

आप बस इसके माध्यम से लूप कर सकते हैं:

>>> gen = (i for i in range(1, 4))
>>> for i in gen: print i
1
2
3

लेकिन ध्यान रहे, कि आप केवल एक बार ही लूप कर सकते हैं। अगली बार जनरेटर खाली होगा:

>>> for i in gen: print i
>>> 

4

बस इसे किसी अन्य पुनरावृत्ति की तरह व्यवहार करें:

for val in function_that_returns_a_generator(p1, p2):
    print val

ध्यान दें कि if gen:यह हमेशा सच होगा, इसलिए यह एक झूठी परीक्षा है


2

यदि आप मैन्युअल रूप से जनरेटर के माध्यम से स्थानांतरित करना चाहते हैं (यानी, प्रत्येक लूप के साथ मैन्युअल रूप से काम करने के लिए) तो आप ऐसा कुछ कर सकते हैं:

    from pdb import set_trace

    for x in gen:
        set_trace()
        #do whatever you want with x at the command prompt
        #use pdb commands to step through each loop of the generator e.g., >>c #continue   

1
पीडीबी आयात से set_trace # नहीं () :)
व्लाद के।

1

अन्य उत्तर जटिल परिदृश्यों के लिए अच्छे हैं। यदि आप आइटम को सूची में स्ट्रीम करना चाहते हैं:

x = list(generator)

(या, यदि आप सामान को बस करने के लिए जनरेटर को ट्रिगर करना चाहते हैं, तो बस list(generator)

सरल प्रीप्रोसेसिंग के लिए, सूची बोध का उपयोग करें:

x = [tup[0] for tup in generator]

या जब आप सरल कार्यों को निष्पादित करना चाहते हैं:

# didn't assign to variable b/c we don't care about what the print() function returns
[print(x) for x in gen]
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.