2010-01-13 11 views
31

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

print True     # outputs true 
True = False; print True # outputs false 
True = True;  print True # outputs false 
True = not True; print True # outputs true 

क्या कोई इस अजीब व्यवहार को समझा सकता है? मुझे लगता है कि इसमें पाइथन के ऑब्जेक्ट मॉडल के साथ कुछ करना है लेकिन मुझे यकीन नहीं है।

यह सिग्विन के तहत संस्करण 2.5.2 है।

+18

कि अच्छे पुराने मजाक '#define सच FALSE' नहीं है यहां कार्रवाई में? – Amarghosh

+2

संस्करण 3 में अभिसरण सही = गलत एक सिंटैक्स त्रुटि उठाता है, इसलिए मुझे लगता है कि आपका प्रश्न संस्करण 2 – jab

+2

को संदर्भित करता है इसके बारे में क्या अजीब बात है? विस्तृत करने के लिए परवाह? – ghostdog74

उत्तर

73

पायथन इन दोनों (दूसरों के बीच) निर्मित वस्तुओं में है। वे सिर्फ वस्तुएं हैं; शुरुआत में, उनके पास अभी तक कोई नाम नहीं है, लेकिन यह जानने के लिए कि हम क्या देखते हैं, चलो उन्हें 0x600D और 0xBAD पर कॉल करें।

एक अजगर (2.x) स्क्रिप्ट निष्पादित करने के लिए शुरू करने से पहले, नाम True वस्तु 0x600D करने के लिए बाध्य हो जाता है, और नाम False वस्तु 0xBAD करने के लिए बाध्य हो जाता है, इसलिए जब कार्यक्रम True को संदर्भित करता है, यह 0x600D पर लग रहा है ।

क्योंकि 0x600D और 0xBAD जानते हैं कि वे आम तौर पर नाम True और False द्वारा किया जाता है, कि क्या वे उत्पादन जब वे मुद्रित करने के है, अर्थात 0x600D रिटर्न 'True' और इतने पर की __str__ विधि।

True = False 

अब True नाम को एक अलग वस्तु से बांधता है। अब से, दोनों नाम True और False उसी ऑब्जेक्ट को संदर्भित करते हैं 0xBAD, जो मुद्रित होने पर False आउटपुट करता है।

True = True 

वास्तव में कुछ भी नहीं है: यह ऑब्जेक्ट नाम True से जाना जाता है और इस वस्तु के लिए नए (और पुराने) नाम True बांधता है। चूंकि (पिछले चरण की वजह से) True इस से पहले 0xBAD को संदर्भित करता है, इसके बाद भी यह 0xBAD को संदर्भित करता है। इसलिए, प्रिंटिंग अभी भी False आउटपुट करता है।

True = not True 

पहले उद्देश्य यह है कि नाम True के लिए बाध्य है, जो 0xBAD है लेता है। यह इस ऑब्जेक्ट को not ऑपरेटर को देता है। not0xBAD को संदर्भित करने के लिए यहां किस नाम का उपयोग नहीं किया जाता है (या पता है), यह केवल जानता है कि 0xBAD दिए जाने पर इसे 0x600D वापस करना चाहिए।यह वापसी मान तब असाइनमेंट ऑपरेटर = को दिया जाता है, इस ऑब्जेक्ट पर True नाम बाध्यकारी।

नाम True नाम से अब एक बार 0x600D ऑब्जेक्ट को संदर्भित करता है, print TrueTrue आउटपुट को कॉल करता है, और दुनिया फिर से अच्छी है।

+16

@paxdiablo: आप "निमोनिक्स" के बारे में क्या बात कर रहे हैं? वे मेमोरी एड्रेस हैं जहां हर अच्छे पायथन कार्यान्वयन को इन ऑब्जेक्ट्स को रखना चाहिए :- – balpha

+0

@ user127555 मुझे पता है; "असाइनमेंट एक अभिव्यक्ति नहीं है" मेरी पसंदीदा पायथन सुविधाओं में से एक है। लेकिन "कोई असाइनमेंट ऑपरेटर" के संबंध में: यहां तक ​​कि [आधिकारिक दस्तावेज़] (https://docs.python.org/2/reference/simple_stmts.html) उस नाम से इसका संदर्भ लें। – balpha

17

2.x में, सही और गलत कीवर्ड नहीं हैं, इसलिए इस तरह से अंतर्निहित छाया को छाया करना संभव है।

41

बजाय इस कल्पना कीजिए:

A = True 
B = False 

print A   # true 
A = B; print A # false 
A = A; print A # false, because A is still false from before 
A = not A; print A # true, because A was false, so not A is true 

सटीक एक ही बात चल रही है, लेकिन अपने संस्करण में यह भ्रामक है, क्योंकि आप की उम्मीद नहीं है कि आप यह सच है और झूठे को फिर से परिभाषित कर सकते हैं।

>>> import keyword 
>>> keyword.iskeyword('True') 
False 

यह नहीं है के बाद से (मेरे संस्करण में), बताए यह सच है = झूठी बस का अर्थ है "यह सच है" एक और "चर" नाम है:

11

आप देख सकते हैं कि क्या सही/गलत एक कीवर्ड है।

+1

बस एक नोट है कि आपको शायद 'keyword.iskeyword (' True ') का उपयोग करना चाहिए। इसके बजाए एक उदाहरण के रूप में, चूंकि अधिकांश वास्तविक कीवर्ड वहां उपयोग किए जाने पर एक सिंटेक्स त्रुटि प्रदान करेंगे। –

+0

@Ig, sure.thanks – ghostdog74

+2

नोट: यह पायथन 3 में तय है, ट्रू एक [कीवर्ड] (https://docs.python.org/3/reference/lexical_analysis.html#keywords) है। –

0

आप आसानी से मूल मूल्यों सरल बूलियन तुलना का उपयोग कर बहाल कर सकते हैं:

True = 1==1 
False = 1==0 

या bools को पूर्णांक शाब्दिक परिवर्तित करके:

True = bool(1) # actually every number except 0 works 
False = bool(0) 
संबंधित मुद्दे