2010-02-19 77 views
33
int x = 10; 
x += x--; 

सी #/नेट में, यह बराबर क्यों बराबर है? (मैं जानबूझ कर जवाब बाहर जा रहा हूँ ताकि आप अनुमान लगा और देखें कि क्या तुम सही हो सकता है) इस बयान परint x = 10; एक्स + = एक्स--; नेट में - क्यों?

+16

ऐसा नहीं है कि जिस तरह से व्यवहार करती है, क्योंकि आप ऐसा कुछ कभी नहीं करना चाहिए, और इस तरह के व्यवहार के रूप में अप्रासंगिक है। –

+0

दिलचस्प सवाल! – Kevin

+0

मुझे खुद को दूसरा अनुमान नहीं लगाया जाना चाहिए। जब तक मैंने इसे एक सेकंड के बारे में सोचा तब तक स्पष्ट लग रहा था। 20 सोचने के लिए मेरा तर्क यह था कि संदर्भ के बाद तक कमी नहीं हुई और फिर मैंने यह सोचने से कहा कि मूल संदर्भ कम हो जाएगा जब ऑपरेशन कॉम्प्लेटेड हो जाएगा लेकिन यह एक मूल्य प्रकार है लेकिन मुझे लगता है 19. मुझे मूर्खतापूर्ण। –

उत्तर

53

देखो:

x = x + x--; 
:

x += x--; 

इस के बराबर है

कौन सा के बराबर है:

int a1 = x; // a1 = 10, x = 10 
int a2 = x--; // a2 = 10, x = 9 
x = a1 + a2; // x = 20 

तो x 20 बाद में है - और यह कल्पना द्वारा गारंटीकृत है।

बहुत अधिक गारंटीकृत है, हालांकि कल्पना द्वारा नहीं, यह है कि इस तरह के कोड का उपयोग करने वाले किसी भी व्यक्ति को उनके सहयोगियों द्वारा हमला किया जाएगा। हां, यह अच्छा है कि परिणाम अनुमानित है। नहीं, का उपयोग करने के लिए यह अच्छा नहीं है।

+9

कोई उचित नहीं ... स्कीट को इन सवालों के जवाब देने की अनुमति नहीं दी जानी चाहिए। : पी – CAbbott

+1

हाहा, कोई स्कीट की अनुमति नहीं दी जानी चाहिए !!! लालची! haha। – Eric

+3

@CAbbott - दुर्भाग्य से x-- और --x के बीच अंतर को समझने के लिए कोई और नहीं लगता है! –

10

specs 7.13.2

से यदि चयनित ऑपरेटर की वापसी प्रकार परोक्ष एक्स के प्रकार के लिए परिवर्तनीय है, आपरेशन, एक्स = एक्स सेशन y के रूप में मूल्यांकन, सिवाय इसके कि एक्स केवल एक बार मूल्यांकन किया जाता है है।

तो अपने बयान x = x + x--; जो बाएँ-से-सही क्रम में मूल्यांकन किया है और जवाब देता है 20.

नोट वहाँ भी --x और x-- यहाँ बीच एक अंतर है कि है के बराबर है। यदि आपने x += --x; लिखा था तो यह x = x + --x के बराबर होगा; तो आपको 1 9 मिल जाएगा। ऐसा इसलिए है क्योंकि x का मान कम हो गया है और परिणामी मान अभिव्यक्ति में उपयोग किया जाता है (x-- के विपरीत जहां x का मूल मान अभिव्यक्ति में उपयोग किया जाता है)।

यह अभिव्यक्ति x = x + --x + x 28 दे देंगे क्योंकि तीसरी बार चौथी बार (टिप्पणी देखें) एक्स यह है 9.

+0

शायद आपका मतलब 20 था? 10 वास्तव में आश्चर्यजनक होगा ..;) – Francesco

+0

@ फ्रांसेस्को: टाइपो, तय। अब मैंने एक और पैराग्राफ जोड़ा है और * * * वास्तव में spec उद्धृत करने के लिए 10. –

+0

+1 होने का मतलब है। –

14

20 मूल्यांकन किया जाता है; "-" तब तक नहीं होता जब तक कि सबकुछ मूल्यांकन न हो जाए, और वह मान बराबर के बाएं हाथ से ओवरराइट हो जाता है।

+11

आपका नाम जॉन स्कीट नहीं है, लेकिन मैं वैसे भी ऊपर उठ जाऊंगा। –

+4

हालांकि आपको सही उत्तर मिल गया है, लेकिन आपको जो तर्क मिला वह गलत है। "सबकुछ मूल्यांकन होने के बाद तक नहीं होता" भ्रामक है। विशेष रूप से, कमी 9 से एक्स के असाइनमेंट से पहले होती है, जो 10 और 10 के अतिरिक्त होने से पहले होती है, जो 20 से x के असाइनमेंट से पहले होती है। कमी की गणना एक अतिरिक्त और दो असाइनमेंट से पहले होती है, इसलिए यह कहना सही नहीं हो सकता है कि यह तब तक नहीं होता जब तक कि * सबकुछ * मूल्यांकन नहीं हो जाता। –

0

उत्तर 20 है। और टॉम, आप वास्तव में आश्चर्यचकित नहीं हैं क्योंकि आपके प्रश्नों का अर्थ है, है ना? और आप में से जो उत्तर मान रहे हैं 1 9 - मुझे लगता है कि आप x + = --x के साथ उलझन में हैं;

+2

वे जो उलझन में हैं, वे संभवतः --x नहीं हैं, बल्कि, "कमी x" का दुष्प्रभाव + = ऑपरेटर के बाएं हाथ की गणना के पहले या बाद में होता है। भाषा में जहां x + = x-- का मूल्यांकन दाएं से बाएं किया जाता है, आप पहले x की गणना करते हैं, जो 10 है, और 9 से x असाइन करें। फिर आप बाईं ओर की गणना करते हैं, जो अब 9 है। और अब आप 9 से 10 जोड़ते हैं और एक्स को असाइन करते हैं, इसलिए, 19. सी # गारंटी देता है कि अभिव्यक्तियों का मूल्यांकन बाएं से दाएं है। सी ++ नहीं करता है; एक सी ++ कंपाइलर यह चुनने पर दाएं से बाएं का मूल्यांकन कर सकता है, और 1 9 और 20 दोनों कानूनी परिणाम हैं। –

+0

एरिक। मैं विश्वास करता हूँ की आप सही है। मैं और अधिक सहमत नहीं हो सका। – Eric

15

जॉन बिल्कुल सही है।

1) subexpressions हमेशा मूल्यांकन किया जाता है बाएं से दाएं:

एक अच्छा तरीका यह के बारे में सोचना याद करने के लिए है। अवधि। एक subexpression का मूल्यांकन एक दुष्प्रभाव प्रेरित कर सकते हैं।

2) ऑपरेटरों का निष्पादन हमेशा ब्रांड्स, प्राथमिकता और सहयोगीता द्वारा संकेतित क्रम में किया जाता है। ऑपरेटरों का निष्पादन दुष्प्रभाव उत्पन्न कर सकता है।

+ = के बाईं ओर "x" बाएं सबसे उप-संपीड़न है, और इसलिए नियम (1) लागू होता है। इसका मूल्य पहले गणना की जाती है - 10.

x-- के दाईं ओर x = बाएं से दाएं क्रम में अगला है, इसलिए इसका मूल्यांकन किया जाता है। एक्स का मान 10 है, और साइड इफेक्ट यह है कि एक्स 9 हो जाता है। यह ऐसा होना चाहिए, क्योंकि - + = से अधिक प्राथमिकता है, इसलिए इसका दुष्प्रभाव पहले चलता है।

अंत में, + = रन का दुष्प्रभाव आखिरी है। दो ऑपरेंड 10 और 10 थे, इसलिए परिणाम 20 से x असाइन करना है।

मुझे इस समय के बारे में प्रश्न मिलते हैं। याद रखें, नियम बहुत सरल हैं: subexpressions बाएं से दाएं, ऑपरेटरों क्रम में ऑपरेटर, अवधि।

विशेष रूप से, ध्यान दें कि आमतौर पर बताए गए तर्क "ऑपरेटर पोस्टफिक्स है और इसलिए सबकुछ के बाद चलता है" गलत तर्क है। मैं चर्चा करता हूं कि नीचे दिए गए लेखों में यह गलत क्यों है।

यहां कुछ लेख मैं इस विषय पर लिखा है इस प्रकार हैं:

http://blogs.msdn.com/ericlippert/archive/tags/precedence/default.aspx

+0

अतिरिक्त सी # में अनुक्रम बिंदु है? आप लोगों को अनुक्रम बिंदुओं को समझे बिना कोड लिखने की अनुमति दे रहे हैं। निश्चित रूप से दुनिया का अंत हाथ में है। –

संबंधित मुद्दे