एक C++ पहचानकर्ता में अंडरस्कोर का उपयोग करने के नियम क्या हैं?




standards underscores (4)

यह किसी भी प्रकार के उपसर्ग के साथ सदस्य चर का नाम देने के लिए सी ++ में आम है, यह तथ्य बताता है कि वे स्थानीय चर या पैरामीटर के बजाय सदस्य चर हैं। यदि आप किसी एमएफसी पृष्ठभूमि से आए हैं, तो आप शायद m_foo उपयोग m_foo । मैंने कभी-कभी myFoo भी देखा है।

सी # (या संभवतः सिर्फ .NET) _foo में, बस एक अंडरस्कोर का उपयोग करने की अनुशंसा करता है। क्या यह सी ++ मानक द्वारा अनुमत है?


नामों की टक्कर से बचने के नियम सी ++ मानक (स्ट्रॉस्ट्रप बुक देखें) में हैं और सी ++ गुरु (सटर, इत्यादि) द्वारा उल्लिखित हैं।

व्यक्तिगत नियम

क्योंकि मैं मामलों से निपटना नहीं चाहता था, और एक साधारण नियम चाहता था, मैंने एक व्यक्तिगत व्यक्ति बनाया है जो सरल और सही दोनों है:

प्रतीक का नामकरण करते समय, आप कंपाइलर / ओएस / मानक पुस्तकालयों के साथ टकराव से बचेंगे यदि आप:

  • अंडरस्कोर के साथ कभी भी प्रतीक शुरू न करें
  • अंदर लगातार दो अंडरस्कोर के साथ एक प्रतीक का नाम कभी नहीं।

बेशक, अपने कोड को एक अद्वितीय नामस्थान में डालने से टकराव से बचने में भी मदद मिलती है (लेकिन बुराई मैक्रोज़ के खिलाफ सुरक्षा नहीं होगी)

कुछ उदाहरण

(मैं मैक्रोज़ का उपयोग करता हूं क्योंकि वे सी / सी ++ प्रतीकों के अधिक कोड-प्रदूषण हैं, लेकिन यह परिवर्तनीय नाम से कक्षा के नाम से कुछ भी हो सकता है)

#define _WRONG
#define __WRONG_AGAIN
#define RIGHT_
#define WRONG__WRONG
#define RIGHT_RIGHT
#define RIGHT_x_RIGHT

सी ++ 0 एक्स ड्राफ्ट से निकालें

n3242.pdf फ़ाइल से (मुझे उम्मीद है कि अंतिम मानक पाठ समान होना चाहिए):

17.6.3.3.2 वैश्विक नाम [वैश्विक नाम]

नाम और फ़ंक्शन हस्ताक्षर के कुछ सेट हमेशा कार्यान्वयन के लिए आरक्षित होते हैं:

- प्रत्येक नाम जिसमें डबल अंडरस्कोर _ _ होता है या अंडरस्कोर के साथ शुरू होता है उसके बाद अपरकेस अक्षर (2.12) किसी भी उपयोग के लिए कार्यान्वयन के लिए आरक्षित होता है।

- अंडरस्कोर से शुरू होने वाला प्रत्येक नाम वैश्विक नामस्थान में नाम के रूप में उपयोग के लिए कार्यान्वयन के लिए आरक्षित है।

लेकिन:

17.6.3.3.5 उपयोगकर्ता परिभाषित शाब्दिक प्रत्यय [usrlit.suffix]

शाब्दिक प्रत्यय पहचानकर्ता जो अंडरस्कोर से शुरू नहीं होते हैं वे भविष्य के मानकीकरण के लिए आरक्षित हैं।

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


नियम (जो सी ++ 11 में नहीं बदला गया):

  • कार्यान्वयन मैक्रोज़ के रूप में उपयोग के लिए, किसी भी दायरे में आरक्षित:
    • अंडरस्कोर से शुरू होने वाले पहचानकर्ता तुरंत अपरकेस अक्षर द्वारा पीछा करते हैं
    • आसन्न अंडरस्कोर (या "डबल अंडरस्कोर" युक्त पहचानकर्ता)
  • वैश्विक नामस्थान में आरक्षित:
    • अंडरस्कोर से शुरू होने वाले पहचानकर्ता
  • इसके अलावा, std नेमस्पेस में सबकुछ आरक्षित है। (हालांकि, आपको टेम्पलेट विशेषज्ञता जोड़ने की अनुमति है।)

2003 सी ++ मानक से:

17.4.3.1.2 वैश्विक नाम [lib.global.names]

नाम और फ़ंक्शन हस्ताक्षर के कुछ सेट हमेशा कार्यान्वयन के लिए आरक्षित होते हैं:

  • प्रत्येक नाम जिसमें डबल अंडरस्कोर ( __ ) होता है या अंडरस्कोर के साथ शुरू होता है उसके बाद अपरकेस अक्षर (2.11) किसी भी उपयोग के लिए कार्यान्वयन के लिए आरक्षित होता है।
  • अंडरस्कोर से शुरू होने वाला प्रत्येक नाम वैश्विक नामस्थान में नाम के रूप में उपयोग के लिए कार्यान्वयन के लिए आरक्षित है। 165

165) ऐसे नाम नेमस्पेस ::std (17.4.3.1) में भी आरक्षित हैं।

चूंकि सी ++ सी मानक (1.1 / 2, सी ++ 03) पर आधारित है और सी 99 एक मानक संदर्भ (1.2 / 1, सी ++ 03) है, यह 1 999 सी मानक से भी लागू होता है:

7.1.3 आरक्षित पहचानकर्ता

प्रत्येक हेडर अपने संबंधित उपखंड में सूचीबद्ध सभी पहचानकर्ताओं को घोषित करता है या परिभाषित करता है, और वैकल्पिक रूप से किसी भी उपयोग के लिए या फ़ाइल स्कोप पहचानकर्ता के रूप में उपयोग के लिए आरक्षित हमेशा जुड़े हुए लाइब्रेरी दिशानिर्देशों में सूचीबद्ध पहचानकर्ताओं को पहचानता या परिभाषित करता है।

  • सभी पहचानकर्ता जो अंडरस्कोर से शुरू होते हैं और या तो अपरकेस अक्षर या अन्य अंडरस्कोर हमेशा किसी भी उपयोग के लिए आरक्षित होते हैं।
  • अंडरस्कोर से शुरू होने वाले सभी पहचानकर्ता हमेशा सामान्य और टैग नाम रिक्त स्थान दोनों में फ़ाइल स्कोप वाले पहचानकर्ता के रूप में उपयोग के लिए आरक्षित होते हैं।
  • निम्न में से किसी भी उपखंड (भविष्य में लाइब्रेरी दिशानिर्देशों सहित) में प्रत्येक मैक्रो नाम निर्दिष्ट के लिए आरक्षित है यदि उसके किसी भी संबंधित शीर्षलेख शामिल हैं; जब तक स्पष्ट रूप से अन्यथा न कहा गया हो (7.1.4 देखें)।
  • निम्नलिखित उपखंडों (भविष्य की लाइब्रेरी दिशानिर्देशों सहित) में बाहरी लिंकेज वाले सभी पहचानकर्ता हमेशा बाहरी संपर्क के साथ पहचानकर्ता के रूप में उपयोग के लिए आरक्षित होते हैं। 154
  • निम्नलिखित उपखंडों (भविष्य में लाइब्रेरी दिशानिर्देशों सहित) में सूचीबद्ध फ़ाइल स्कोप के साथ प्रत्येक पहचानकर्ता एक मैक्रो नाम के रूप में उपयोग के लिए आरक्षित है और उसी नाम स्थान में फ़ाइल स्कोप के साथ पहचानकर्ता के रूप में है यदि उसके किसी भी संबंधित शीर्षलेख शामिल हैं।

कोई अन्य पहचानकर्ता आरक्षित नहीं हैं। यदि कार्यक्रम किसी संदर्भ में पहचानकर्ता घोषित करता है या परिभाषित करता है जिसमें यह आरक्षित है (7.1.4 द्वारा अनुमत के अलावा), या एक आरक्षित पहचानकर्ता को मैक्रो नाम के रूप में परिभाषित करता है, तो व्यवहार अपरिभाषित होता है।

यदि कार्यक्रम ऊपर सूचीबद्ध पहले समूह में पहचानकर्ता की किसी भी मैक्रो परिभाषा को हटाता है ( #undef साथ), व्यवहार अपरिभाषित है।

154) बाहरी लिंकेज वाले आरक्षित पहचानकर्ताओं की सूची में math_errhandling , math_errhandling , math_errhandling , और va_end

अन्य प्रतिबंध लागू हो सकते हैं। उदाहरण के लिए, POSIX मानक बहुत से पहचानकर्ता सुरक्षित रखता है जो सामान्य कोड में दिखाई देने की संभावना है:

  • पूंजी E शुरू होने वाले नाम एक अंक या अपरकेस अक्षर का पालन करते हैं:
    • अतिरिक्त त्रुटि कोड नामों के लिए इस्तेमाल किया जा सकता है।
  • नाम जो कि किसी के साथ शुरू होता is या उसके बाद लोअरकेस अक्षर होता है
    • अतिरिक्त चरित्र परीक्षण और रूपांतरण कार्यों के लिए इस्तेमाल किया जा सकता है।
  • नाम जो LC_ साथ एक अपरकेस अक्षर के बाद शुरू होते हैं
    • लोकेल विशेषताओं को निर्दिष्ट अतिरिक्त मैक्रोज़ के लिए इस्तेमाल किया जा सकता है।
  • f या l साथ प्रत्यय सभी मौजूदा गणित कार्यों के नाम आरक्षित हैं
    • इसी तरह के कार्यों के लिए जो क्रमशः फ्लोट और लंबे डबल तर्कों पर काम करते हैं।
  • SIG साथ शुरू होने वाले नाम एक अपरकेस पत्र के बाद आरक्षित हैं
    • अतिरिक्त सिग्नल नामों के लिए।
  • SIG_ साथ शुरू होने वाले नाम एक अपरकेस अक्षर के बाद आरक्षित हैं
    • अतिरिक्त सिग्नल कार्यों के लिए।
  • wcs , mem , या wcs साथ शुरू होने वाले नाम लोअरकेस अक्षर के बाद आरक्षित हैं
    • अतिरिक्त स्ट्रिंग और सरणी कार्यों के लिए।
  • PRI या SCN साथ शुरू होने वाले नाम किसी भी लोअरकेस अक्षर या X आरक्षित हैं
    • अतिरिक्त प्रारूप विनिर्देशक मैक्रोज़ के लिए
  • _t साथ समाप्त होने वाले नाम आरक्षित हैं
    • अतिरिक्त प्रकार के नामों के लिए।

अपने नामों के लिए इन नामों का उपयोग करते समय अभी समस्या नहीं हो सकती है, वे उस मानक के भविष्य के संस्करणों के साथ संघर्ष की संभावना बढ़ाते हैं।

व्यक्तिगत रूप से मैं सिर्फ अंडरस्कोर के साथ पहचानकर्ता शुरू नहीं करता हूं। मेरे नियम के लिए नया जोड़ा: कहीं भी डबल अंडरस्कोर का उपयोग न करें, जो कि आसान है क्योंकि मैं शायद ही कभी अंडरस्कोर का उपयोग करता हूं।

इस आलेख पर शोध करने के बाद मैं अब अपने पहचानकर्ताओं को _t साथ समाप्त नहीं कर सकता क्योंकि यह POSIX मानक द्वारा आरक्षित है।

किसी भी पहचानकर्ता के बारे में नियम मुझे आश्चर्यचकित कर रहा है। मुझे लगता है कि यह एक पॉज़िक्स मानक है (अभी तक सुनिश्चित नहीं है) स्पष्टीकरण और आधिकारिक अध्याय और कविता की तलाश में है। यह जीएनयू libtool मैनुअल से है , आरक्षित नाम सूचीबद्ध।

सीज़रबी ने opengroup.org/onlinepubs/009695399/functions/xsh_chap02_02.html आरक्षित प्रतीकों और नोट्स के लिए निम्न लिंक प्रदान किया है कि कई अन्य आरक्षित उपसर्ग और प्रत्यय ... वहां पाए जा सकते हैं। POSIX 2008 आरक्षित प्रतीक यहां परिभाषित किए गए हैं। प्रतिबंध ऊपर दिए गए लोगों की तुलना में कुछ हद तक अधिक हैं।


हां, अंडरस्कोर को पहचानकर्ता में कहीं भी इस्तेमाल किया जा सकता है। मेरा मानना ​​है कि नियम हैं: पहले अक्षर में एजे, एजेड, _ में से कोई और निम्नलिखित वर्णों के लिए + 0-9।

अंडरस्कोर उपसर्ग सी कोड में आम हैं - एक अंडरस्कोर का अर्थ है "निजी", और डबल अंडरस्कोर आमतौर पर कंपाइलर द्वारा उपयोग के लिए आरक्षित होते हैं।


MSDN :

एक पहचानकर्ता की शुरुआत में दो अनुक्रमिक अंडरस्कोर वर्णों (__) का उपयोग, या पूंजी पत्र के बाद एक एकल अंडरस्कोर, सभी क्षेत्रों में सी ++ कार्यान्वयन के लिए आरक्षित है। वर्तमान या भविष्य के आरक्षित पहचानकर्ताओं के संभावित संघर्षों के कारण आपको फ़ाइल स्कोप वाले नामों के लिए लोअरकेस अक्षर के बाद एक अग्रणी अंडरस्कोर का उपयोग करना चाहिए।

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

यह स्पष्ट रूप से सी ++ मानक की धारा 17.4.3.1.2 से लिया गया है, लेकिन मुझे पूर्ण मानक ऑनलाइन के लिए मूल स्रोत नहीं मिल रहा है।

यह सवाल भी देखें।





c++-faq