बयान के दौरान अजगर पर बुरा आरोप


321

मैंने देखा है कि पायथन में निम्न कोड कानूनी है। मेरा सवाल यह है कि क्यों? क्या कोई खास वजह है?

n = 5
while n != 0:
    print n
    n -= 1
else:
    print "what the..."

5
@detly: ऐसा इसलिए है क्योंकि ज्यादातर लोग इस निर्माण से बचते हैं। :) मेरा मानना ​​है कि गुइडो ने Py3k प्रक्रिया के दौरान उल्लेख किया है कि, बहुत कम से कम, elseइस उपयोग के लिए शब्द का चुनाव एक उल्लेखनीय रूप से बुरा विचार था, और यह कि वे इनमें से कुछ भी नहीं करेंगे।
निकोलस नाइट

5
@ निकोलस नाइट - हाँ, हालांकि यह आकर्षक है, यह शायद कुछ होगा जो मैंने पहली नज़र में ही समझ लिया था। किसी भी अन्य गरीब व्यक्ति को भाषा की युक्ति को देखना होगा, या समय में वापस जाना होगा और यहां एक सवाल पोस्ट करना होगा- Sta- heeeeey ...
det

8
'और' चुनने के पीछे विचार यह है कि इस निर्माण को अक्सर लूप के अंदर 'अगर X: ब्रेक' के साथ संयोजन में उपयोग किया जाता है। चूँकि 'और' खंड को निष्पादित किया जाता है यदि हम लूप से बाहर नहीं निकलते हैं, तो यह 'if' के लिए थोड़े-थोड़े 'और' बनाता है।
जोनाथन हार्टले

12
उन्हें इसका नाम बदलना चाहिए after:
n

जवाबों:


388

elseखंड केवल मार डाला है जब आपके है whileहालत झूठी हो जाता है। यदि आप breakलूप से बाहर हैं, या यदि कोई अपवाद उठाया गया है, तो इसे निष्पादित नहीं किया जाएगा।

इसके बारे में सोचने का एक तरीका यह है कि क्या शर्त के संबंध में एक और तरीका है:

if condition:
    handle_true()
else:
    handle_false()

लूपिंग निर्माण के अनुरूप है:

while condition:
    handle_true()
else:
    # condition is false now, handle and go on with the rest of the program
    handle_false()

एक उदाहरण की तर्ज पर हो सकता है:

while value < threshold:
    if not process_acceptable_value(value):
        # something went wrong, exit the loop; don't pass go, don't collect 200
        break
    value = update(value)
else:
    # value >= threshold; pass go, collect 200
    handle_threshold_reached()

42
"अन्य खंड केवल तब निष्पादित किया जाता है जब आपकी स्थिति झूठी हो जाती है।" यहाँ शब्द का तात्पर्य है कि आपका समय राज्य सत्य से असत्य की स्थिति में जाता है और अन्य की तुलना में निष्पादित किया जाएगा। हालाँकि, यदि कभी सत्य नहीं होता है, तब भी अन्य खंड को क्रियान्वित किया जाएगा।
user597608

pseudocode तो मुझे सही करें अगर मैं गलत हूं, लेकिन यह बिल्कुल वैसा ही है, while {} something सिवाय इसके कि somethingअगर आप पाश breakमें हैं तो छोड़ दिया जाएगा while
डैनियल कापलान

2
शायद सबसे सटीक स्यूडोकोड होगा: जबकि (सच्चा) {अगर (कोंड) {हैंडल_ट्रू (); } और {handle_false (); टूटना; }}
विनग्रेसिया

2
"पास मत जाओ, 200 मत इकट्ठा करो", हाहा, हर कोई जानता है कि यह कहाँ से है एक अच्छा बचपन था
स्टीफन ऑक्टेवियन

102

elseयदि आप एक ब्लॉक सामान्य रूप से बाहर निकलते हैं, पाश हालत मार या एक कोशिश ब्लॉक के नीचे से गिरकर खंड निष्पादित किया जाता है। इसे निष्पादित नहीं किया जाता है यदि आप किसी ब्लॉक से breakया returnबाहर निकलते हैं, या एक अपवाद बढ़ाते हैं। यह न केवल जबकि छोरों के लिए काम करता है, बल्कि ब्लॉक का भी प्रयास करता है।

आप इसे आमतौर पर उन जगहों पर पाते हैं, जहां आमतौर पर आप एक लूप से जल्दी बाहर निकल जाते हैं, और लूप के अंत से बाहर चलना एक अप्रत्याशित / असामान्य अवसर होता है। उदाहरण के लिए, यदि आप किसी मूल्य की तलाश करने वाली सूची से गुजर रहे हैं:

for value in values:
    if value == 5:
        print "Found it!"
        break
else:
    print "Nowhere to be found. :-("

1
वास्तव में ऐसी चीज के लिए एक काफी उपयोगी निर्माण। न जाने कितनी बार मैंने found_it=Falseएक लूप की शुरुआत में डाल दिया है , और फिर एक अगर found_itअंत में जाँच करें
क्रंचर

42

इसके जवाब में Is there a specific reason?, यहां एक दिलचस्प अनुप्रयोग है: लूपिंग के कई स्तरों को तोड़ना।

यहां बताया गया है कि यह कैसे काम करता है: बाहरी लूप के अंत में एक ब्रेक होता है, इसलिए इसे केवल एक बार निष्पादित किया जाएगा। हालांकि, अगर आंतरिक लूप पूरा हो जाता है (कोई विभाजक नहीं मिलता है), तो यह दूसरे विवरण तक पहुंच जाता है और बाहरी ब्रेक कभी नहीं पहुंचता है। इस तरह, आंतरिक लूप का ब्रेक केवल एक के बजाय दोनों छोरों से बाहर निकल जाएगा।

for k in [2, 3, 5, 7, 11, 13, 17, 25]:
    for m in range(2, 10):
        if k == m:
            continue
        print 'trying %s %% %s' % (k, m)
        if k % m == 0:
            print 'found a divisor: %d %% %d; breaking out of loop' % (k, m)
            break
    else:
        continue
    print 'breaking another level of loop'
    break
else:
    print 'no divisor could be found!'

दोनों whileऔर forछोरों के लिए, elseबयान को अंत में निष्पादित breakकिया जाता है , जब तक कि इसका उपयोग नहीं किया गया था।

ज्यादातर मामलों में ऐसा करने के लिए बेहतर तरीके हैं (इसे किसी फ़ंक्शन में लपेटना या अपवाद उठाना), लेकिन यह काम करता है!


1
मैं कम नहीं था, लेकिन मुझे लगता है कि मुझे पता है कि किसी ने क्यों किया। आप सवाल का जवाब नहीं दे रहे हैं और आप केवल 2 लाइनों के विवरण के साथ कोड की 14 लाइनें प्रदान कर रहे हैं। यदि पूछे गए प्रश्न की प्रासंगिकता है तो आप हमें नहीं बता रहे हैं ...
BlueEel

1
@BlueEel प्रतिक्रिया के लिए धन्यवाद! मैंने कोड के बारे में और स्पष्टीकरण जोड़ा है, और इसे और अधिक स्पष्ट किया है कि यह प्रश्न का उत्तर कैसे देता है (क्योंकि यह इसका उत्तर देता है)।
मार्क

आप अपने कोड को संदर्भ में रखने में कामयाब रहे और यद्यपि आप उन सभी सवालों के जवाब नहीं दे रहे हैं जो मैं अब प्रासंगिकता देख रहा हूं। मैंने आपके उत्तर को बढ़ा दिया क्योंकि यह अब नए लोगों और नौसिखियों के लिए उपयोगी है (जैसा कि अजगर के संबंध में है)। - धन्यवाद, मैंने कुछ सीखा।
ब्लू ईल

मुझे सरल आवेदन पसंद है - अब मैं देखता हूं कि कोई इसका उपयोग क्यों कर सकता है। हालाँकि मैंने कभी इसकी ज़रूरत नहीं देखी।
gabe

उदाहरण के लिए / अन्यथा का उपयोग दिखाता है लेकिन सवाल विशेष रूप से / जबकि था ।
इयान गोल्डबी

20

जब स्थिति असत्य का मूल्यांकन करती है तो अन्य-खंड को निष्पादित किया जाता है।

से प्रलेखन :

जब तक कथन एक अभिव्यक्ति के सत्य होने तक दोहराया निष्पादन के लिए उपयोग किया जाता है:

while_stmt ::=  "while" expression ":" suite
                ["else" ":" suite]

यह बार-बार अभिव्यक्ति का परीक्षण करता है और, अगर यह सच है, तो पहले सूट को निष्पादित करता है; यदि अभिव्यक्ति झूठी है (जो पहली बार परीक्षण किया जा सकता है) else, तो क्लॉज का सूट , यदि मौजूद है, तो निष्पादित किया जाता है और लूप समाप्त हो जाता है।

breakपहले सूट में निष्पादित एक बयान elseक्लॉज के सूट को निष्पादित किए बिना लूप को समाप्त करता है । continueपहले सूट में निष्पादित एक स्टेटमेंट, बाकी सुइट को छोड़ देता है और एक्सप्रेशन की जांच करने के लिए वापस चला जाता है।


15

मेरा उत्तर उस पर ध्यान केंद्रित करेगा जब हम / के लिए उपयोग कर सकते हैं-अन्यथा।

पहली नज़र में, ऐसा लगता है कि उपयोग करते समय कोई अलग नहीं है

while CONDITION:
    EXPRESSIONS
print 'ELSE'
print 'The next statement'

तथा

while CONDITION:
    EXPRESSIONS
else:
    print 'ELSE'
print 'The next statement'

क्योंकि print 'ELSE'कथन हमेशा दोनों मामलों में निष्पादित होता है (दोनों जब whileलूप समाप्त होता है या नहीं चलता है)।

फिर, यह केवल भिन्न है जब कथन print 'ELSE'निष्पादित नहीं किया जाएगा। यह तब होता है जब breakकोड ब्लॉक के अंदर होता हैwhile

In [17]: i = 0

In [18]: while i < 5:
    print i
    if i == 2:
        break
    i = i +1
else:
    print 'ELSE'
print 'The next statement'
   ....:
0
1
2
The next statement

यदि भिन्न है:

In [19]: i = 0

In [20]: while i < 5:
    print i
    if i == 2:
        break
    i = i +1
print 'ELSE'
print 'The next statement'
   ....:
0
1
2
ELSE
The next statement

return इस श्रेणी में नहीं है, क्योंकि यह ऊपर के दो मामलों के लिए एक ही प्रभाव करता है।

अपवाद बढ़ाने से भी कोई फर्क नहीं पड़ता है, क्योंकि जब यह उठता है, जहां अगला कोड निष्पादित किया जाएगा अपवाद हैंडलर (ब्लॉक को छोड़कर) में है, तो elseक्लॉज या क्लॉज के ठीक बाद के कोड को whileनिष्पादित नहीं किया जाएगा।


4

मुझे पता है यह पुराना सवाल है लेकिन ...

जैसा कि रेमंड हेटिंगर ने कहा, इसे while/no_breakइसके बजाय कहा जाना चाहिए while/else
मुझे यह समझने में आसानी होती है कि क्या आप इस स्निपेट को देखते हैं।

n = 5
while n > 0:
    print n
    n -= 1
    if n == 2:
        break
if n == 0:
    print n

लूप के बाद की स्थिति की जाँच के बजाय अब हम इसे स्वैप कर सकते हैं elseऔर उस चेक से छुटकारा पा सकते हैं।

n = 5
while n > 0:
    print n
    n -= 1
    if n == 2:
        break
else:  # read it as "no_break"
    print n

मैं हमेशा while/no_breakकोड को समझने के लिए इसे पढ़ता हूं और यह वाक्य रचना मेरे लिए बहुत मायने रखती है।


3

दूसरे खंड को केवल तभी निष्पादित किया जाता है जब स्थिति असत्य हो जाती है।

यहाँ कुछ उदाहरण हैं:

उदाहरण 1: प्रारंभ में स्थिति झूठी है, इसलिए अन्य-खंड को निष्पादित किया जाता है।

i = 99999999

while i < 5:
    print(i)
    i += 1
else:
    print('this')

उत्पादन:

this

उदाहरण 2: जबकि शर्त i < 5 कभी नहीं झूठी क्योंकि बन i == 3टूटता पाश है, तो बाकी-खंड निष्पादित नहीं किया गया था।

i = 0

while i < 5:
    print(i)
    if i == 3:
        break
    i += 1
else:
    print('this')

उत्पादन:

0
1
2
3

उदाहरण 3: जबकि शर्त i < 5 झूठी जब बन गया iथा 5, इसलिए बाकी-खंड मार डाला गया था।

i = 0

while i < 5:
    print(i)
    i += 1
else:
    print('this')

उत्पादन:

0
1
2
3
4
this

0

इस else:कथन को तब ही क्रियान्वित किया जाता है जब और जब लूप अब अपनी स्थिति से मिलता है (आपके उदाहरण में, जब n != 0गलत है)।

तो आउटपुट यह होगा:

5
4
3
2
1
what the...

मुझे पता है, लेकिन इस तरह का समय जावा में काम नहीं करता है। मुझे यह काफी दिलचस्प लगता है जब मुझे लगा कि यह पायथन में काम करता है। मैं बस उत्सुक था और तकनीकी कारण जानना चाहता था।
इवान

6
@ इवान: यह इतना नहीं है कि यह जावा में काम नहीं करता है लेकिन यह जावा में मौजूद नहीं है । इसे काम करने के लिए बनाया जा सकता है, अगर कोई इसे भाषा में जोड़ने की कोशिश करता है।
इग्नासियो वाज़केज़-अब्राम्स

1
नहीं, जबकि गलत: .. और .. अभी भी एक और खंड चलाता है। यह कहना अधिक सटीक है: यदि लूप टूट गया है, तो केवल अन्य भाग नहीं है।
सिंह उफिम्त्सेव

0

यदि लूप नहीं टूटता है तो एल्स निष्पादित होता है।

मैं इसे 'रनर' रूपक के साथ सोचना पसंद करता हूं।

"और" फिनिश लाइन को पार करने जैसा है, चाहे आप ट्रैक की शुरुआत या अंत में शुरू किया हो। "अन्य" को केवल तभी निष्पादित नहीं किया जाता है यदि आप बीच में कहीं टूट जाते हैं।

runner_at = 0 # or 10 makes no difference, if unlucky_sector is not 0-10
unlucky_sector = 6
while runner_at < 10:
    print("Runner at: ", runner_at)
    if runner_at == unlucky_sector:
        print("Runner fell and broke his foot. Will not reach finish.")
        break
    runner_at += 1
else:
    print("Runner has finished the race!") # Not executed if runner broke his foot.

मुख्य उपयोग के मामले इस नेस्टेड लूप से बाहर का उपयोग कर रहे हैं या यदि आप कुछ बयान केवल तभी चलाना चाहते हैं यदि लूप कहीं नहीं टूटे (एक असामान्य स्थिति होने के बारे में सोचें)।

उदाहरण के लिए, चर का उपयोग किए बिना एक आंतरिक लूप से बाहर निकलने के तरीके या कोशिश / पकड़ने के लिए निम्नलिखित तंत्र है:

for i in [1,2,3]:
    for j in ['a', 'unlucky', 'c']:
        print(i, j)
        if j == 'unlucky':
            break
    else: 
        continue  # Only executed if inner loop didn't break.
    break         # This is only reached if inner loop 'breaked' out since continue didn't run. 

print("Finished")
# 1 a
# 1 b
# Finished

-1

Better जबकि: और: ’का बेहतर उपयोग पायथन में होना चाहिए यदि कोई लूप 'जबकि’ में निष्पादित नहीं होता है, तो execut और ’स्टेटमेंट निष्पादित होता है। जिस तरह से यह आज काम करता है इसका कोई मतलब नहीं है क्योंकि आप नीचे दिए गए कोड का उपयोग एक ही परिणाम के साथ कर सकते हैं ...

n = 5
while n != 0:
    print n
    n -= 1
print "what the..."

8
नहीं, अंतर यह है कि elseयदि आप लूप का उपयोग कर रहे हैं breakया returnकीवर्ड छोड़ रहे हैं तो ब्लॉक निष्पादित नहीं किया जाएगा । आपके उदाहरण में, printनिष्पादित किया जाएगा भी अगर लूप breakकमांड पर समाप्त हो गया है ।
notsurewhattodo

2
आप वर्णन करते हैं कि अधिकांश लोग यह कैसे चाहते हैं कि यह सुविधा काम करती है, न कि यह वास्तव में कैसे काम करती है!
dotancohen

-2

यह सामाजिक संपर्क के लिए उपयोगी है।

while (Date != "January 1st"):
    time.sleep(1)
else:
    print("Happy new year!")

2
और वास्तव में elseयहाँ का उद्देश्य क्या है ? कोड इसके बिना बिल्कुल वैसा ही करता है।
वॉवानो

यदि आपकी breakउलटी गिनती के दौरान आपकी घड़ी और कैलेंडर , तो उपयोग न करने elseसे आप कहेंगे "नया साल मुबारक हो!" तुरन्त जो कोई मतलब नहीं है।
गुरमीत

@Guimote, "अगर आपकी घड़ी और कैलेंडर break" से आपका क्या तात्पर्य है ? breakकोड में कोई भी नहीं है।
वोवानो
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.