यह अपरिभाषित है क्योंकि यह x
अनुक्रम बिंदुओं के बीच दो बार संशोधित करता है । मानक कहते हैं कि यह अपरिभाषित है, इसलिए यह अपरिभाषित है।
इतना मैं जानता हूं।
लेकिन क्यों?
मेरी समझ यह है कि यह मना करने से कंपाइलर बेहतर अनुकूलन कर सकते हैं। सी का आविष्कार होने पर यह समझ में आ सकता था, लेकिन अब एक कमजोर तर्क की तरह लगता है।
यदि हम आज C को पुष्ट करने के लिए थे, तो क्या हम इसे इस तरह से करेंगे, या इसे बेहतर किया जा सकता है?
या हो सकता है कि एक गहरी समस्या है, जो इस तरह के भावों के लिए लगातार नियमों को परिभाषित करना कठिन बनाता है, इसलिए उन्हें मना करना सबसे अच्छा है?
तो मान लीजिए कि हम आज सी को फिर से मजबूत करने के लिए थे। मैं इस तरह के भावों के लिए सरल नियमों का सुझाव देना चाहता हूं x=x++
, जो मुझे मौजूदा नियमों से बेहतर काम करने के लिए लगता है।
मैं मौजूदा लोगों या अन्य सुझावों की तुलना में सुझाए गए नियमों पर आपकी राय लेना चाहता हूं।
सुझाए गए नियम:
- अनुक्रम बिंदुओं के बीच, मूल्यांकन का क्रम अनिर्दिष्ट है।
- साइड इफेक्ट तुरंत होते हैं।
इसमें कोई अपरिभाषित व्यवहार शामिल नहीं है। अभिव्यक्तियाँ इस मान या उस का मूल्यांकन करती हैं, लेकिन निश्चित रूप से आपकी हार्ड डिस्क को प्रारूपित नहीं करेंगी (अजीब बात है, मैंने कभी ऐसा कार्यान्वयन नहीं देखा है जहाँ x=x++
हार्ड डिस्क को प्रारूपित किया जाता है)।
उदाहरण अभिव्यक्तियाँ
x=x++
- अच्छी तरह से परिभाषित, नहीं बदलता हैx
।
सबसे पहले,x
बढ़ा हुआ है (तुरंत जबx++
मूल्यांकन किया जाता है), तो यह पुराना मूल्य में संग्रहीत होता हैx
।x++ + ++x
-x
दो बार वृद्धि , का मूल्यांकन करता है2*x+2
।
हालाँकि दोनों ओर से पहले मूल्यांकन किया जा सकता है, परिणाम या तोx + (x+2)
(बाईं ओर पहले) या(x+1) + (x+1)
(दाईं ओर पहले) है।x = x + (x=3)
- अनिर्दिष्ट, याx
तो करने के लिए सेट । यदि सही पक्ष का मूल्यांकन पहले किया जाता है, तो । यह भी संभव है कि पहले मूल्यांकन किया जाए, इसलिए यह । या तो मामले में, असाइनमेंट का मूल्यांकन होने पर तुरंत होता है, इसलिए संग्रहीत मूल्य को अन्य असाइनमेंट द्वारा अधिलेखित किया जाता है।x+3
6
x+3
x=3
3+3
x=3
x=3
x+=(x=3)
- अच्छी तरह से परिभाषित,x
6 से सेट।
आप तर्क कर सकते हैं कि यह ऊपर की अभिव्यक्ति के लिए सिर्फ शॉर्टहैंड है।
लेकिन मैं कहूंगा कि इसके+=
बाद निष्पादित होना चाहिएx=3
, और दो भागों में नहीं (पढ़ेंx
, मूल्यांकनx=3
, जोड़ें और स्टोर करें नया मूल्य)।
क्या है फायदा?
कुछ टिप्पणियों ने यह अच्छा मुद्दा उठाया।
मैं निश्चित रूप से ऐसे भाव नहीं सोचता, जैसे x=x++
किसी सामान्य कोड में इस्तेमाल किए जाएं।
वास्तव में, मैं इससे कहीं ज्यादा सख्त हूं - मुझे लगता x++
है कि x++;
अकेले के रूप में एकमात्र अच्छा उपयोग है ।
हालाँकि, मुझे लगता है कि भाषा के नियम यथासंभव सरल होने चाहिए। अन्यथा प्रोग्रामर सिर्फ उन्हें समझ नहीं पाते हैं। नियम को अनुक्रम बिंदुओं के बीच दो बार एक चर को बदलने से मना करना निश्चित रूप से एक नियम है जिसे अधिकांश प्रोग्रामर समझ नहीं पाते हैं।
एक बहुत ही बुनियादी नियम यह है:
यदि A वैध है, और B वैध है, और वे एक वैध तरीके से संयुक्त हैं, तो परिणाम मान्य है।
x
एक वैध एल-मूल्य है, x++
एक वैध अभिव्यक्ति है, और =
एल-मूल्य और एक अभिव्यक्ति को संयोजित करने का एक वैध तरीका है, तो कैसे x=x++
कानूनी नहीं है?
सी मानक यहां अपवाद बनाता है, और यह अपवाद नियमों को जटिल बनाता है। आप stackoverflow.com पर खोज कर सकते हैं और देख सकते हैं कि यह अपवाद लोगों को कितना भ्रमित करता है।
तो मैं कहता हूं - इस भ्रम से छुटकारा पाओ।
=== उत्तर का सारांश ===
ऐसा क्यों करते हैं?
मैंने ऊपर अनुभाग में समझाने की कोशिश की - मैं चाहता हूं कि सी नियम सरल हों।अनुकूलन के लिए संभावित:
यह संकलक से कुछ स्वतंत्रता लेता है, लेकिन मैंने ऐसा कुछ भी नहीं देखा जो मुझे आश्वस्त करता हो कि यह महत्वपूर्ण हो सकता है।
अधिकांश अनुकूलन अभी भी किए जा सकते हैं। उदाहरण के लिए,a=3;b=5;
मानक के आदेश को निर्दिष्ट करते हुए भी, फिर से व्यवस्थित किया जा सकता है। अभिव्यक्ति जैसे किa=b[i++]
अभी भी इसी तरह से अनुकूलित किया जा सकता है।आप मौजूदा मानक को नहीं बदल सकते।
मैं मानता हूँ, मैं नहीं कर सकता। मैंने कभी नहीं सोचा था कि मैं वास्तव में आगे बढ़ सकता हूं और मानकों और संकलक बदल सकता हूं। मैं केवल यह सोचना चाहता था कि क्या चीजें अलग तरीके से हो सकती हैं।
x
अपने आप को असाइन करने के लिए बहुत अधिक बिंदु नहीं है, और यदि आप वेतन वृद्धि चाहते हैं तो आपx
केवल कह सकते हैंx++;
- असाइनमेंट की कोई आवश्यकता नहीं है। मैं कहूंगा कि इसे सिर्फ इसलिए परिभाषित नहीं किया जाना चाहिए क्योंकि यह याद रखना मुश्किल होगा कि क्या होने वाला है।