c++ - "नेमस्पेस std का उपयोग" क्यों बुरा अभ्यास माना जाता है?




namespaces using-directives (20)

मुझे दूसरों द्वारा बताया गया है कि कोड में using namespace std लिखना गलत है, और मुझे इसके बजाय std::cout और std::cin उपयोग करना चाहिए।

using namespace std का using namespace std क्यों खराब अभ्यास माना जाता है? क्या यह अक्षम है या क्या अस्पष्ट चर घोषित करने का जोखिम है (वेरिएबल्स जो समान नाम को std नेमस्पेस में फ़ंक्शन के रूप में साझा करते हैं)? क्या यह प्रदर्शन को प्रभावित करता है?


वैश्विक स्तर पर इसका इस्तेमाल न करें

इसे वैश्विक रूप से उपयोग किए जाने पर ही "बुरा" माना जाता है । इसलिये:

  • आप उस नेमस्पेस को अव्यवस्थित करते हैं जिसमें आप प्रोग्रामिंग कर रहे हैं।
  • जब आप using namespace xyz कई using namespace xyz उपयोग करते हैं, तो पाठकों को यह देखने में कठिनाई होगी कि एक विशेष पहचानकर्ता कहां से आता है।
  • आपके स्रोत कोड के अन्य पाठकों के लिए जो कुछ भी सच है, वह इसके सबसे अधिक पाठक के लिए और भी सत्य है: स्वयं। एक या दो साल में वापस आओ और देखो ...
  • यदि आप केवल using namespace std करने के बारे में बात करते हैं तो हो सकता है कि आप जो भी सामान लेते हैं, उसके बारे में आपको अवगत न हो - और जब आप कोई अन्य #include या एक नए सी ++ संशोधन में जाते हैं तो आपको नाम विवाद मिल सकते हैं जिनके बारे में आपको पता नहीं था।

आप इसे स्थानीय रूप से उपयोग कर सकते हैं

आगे बढ़ें और इसे स्थानीय रूप से (लगभग) स्वतंत्र रूप से उपयोग करें। यह, ज़ाहिर है, आपको std:: की पुनरावृत्ति से रोकता है - और पुनरावृत्ति भी खराब है।

इसे स्थानीय रूप से उपयोग करने के लिए एक मुहावरे

सी ++ 03 में एक मुहावरे - बॉयलरप्लेट कोड था - आपके वर्गों के लिए एक swap फ़ंक्शन लागू करने के लिए। यह सुझाव दिया गया था कि आप वास्तव में using namespace std स्थानीय using namespace std - या कम से कम using std::swap :

class Thing {
    int    value_;
    Child  child_;
public:
    // ...
    friend void swap(Thing &a, Thing &b);
};
void swap(Thing &a, Thing &b) {
    using namespace std;      // make `std::swap` available
    // swap all members
    swap(a.value_, b.value_); // `std::stwap(int, int)`
    swap(a.child_, b.child_); // `swap(Child&,Child&)` or `std::swap(...)`
}

यह निम्नलिखित जादू करता है:

  • संकलक value_ लिए std::swap चयन करेगा, यानी void std::swap(int, int)
  • यदि आपके पास एक अधिभार void swap(Child&, Child&) लागू किया गया है तो संकलक इसे चुन देगा।
  • यदि आपके पास उस ओवरलोड को नहीं है तो कंपाइलर void std::swap(Child&,Child&) और इन्हें सबसे अच्छा स्वैप करने का प्रयास करेगा।

सी ++ 11 के साथ इस पैटर्न का उपयोग करने का कोई कारण नहीं है। एक संभावित अधिभार खोजने और इसे चुनने के लिए std::swap का कार्यान्वयन बदल दिया गया था।


  1. आपको उन लोगों द्वारा लिखे गए कोड को पढ़ने में सक्षम होना चाहिए जिनके पास अलग शैली और सर्वोत्तम प्रथाओं की राय है।

  2. यदि आप केवल कॉउट का उपयोग कर रहे हैं, तो कोई भी उलझन में नहीं आता है। लेकिन जब आपके पास बहुत सारे नामस्थान उड़ते हैं और आप इस कक्षा को देखते हैं और आपको बिल्कुल यकीन नहीं है कि यह क्या करता है, नामस्थान स्पष्ट रूप से टिप्पणी के रूप में कार्य करता है। आप पहली नज़र में देख सकते हैं, 'ओह, यह एक फाइल सिस्टम ऑपरेशन है' या 'नेटवर्क सामान कर रहा है'।


आपकी कक्षाओं की शीर्षलेख फ़ाइलों में using namespace समस्या यह है कि यह उन सभी को मजबूर करता है जो आपकी कक्षाओं (अपनी शीर्षलेख फ़ाइलों को शामिल करके) का उपयोग करना चाहते हैं ताकि वे 'अन्य' नामों को भी 'उपयोग' (यानी सबकुछ देख सकें)।

हालांकि, आप अपने (निजी) * .cpp फ़ाइलों में एक उपयोग कथन डालने के लिए स्वतंत्र महसूस कर सकते हैं।

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

उपयोगिता निर्देश विरासत सी ++ कोड के लिए मौजूद है और नामस्थानों में संक्रमण को कम करने के लिए है, लेकिन संभवतः आप इसे नियमित रूप से अपने नए सी ++ कोड में नहीं उपयोग करना चाहिए।

एफएक्यू दो विकल्पों का सुझाव देता है:

  • एक उपयोग-घोषणा:

    using std::cout; // a using-declaration lets you use cout without qualification
    cout << "Values:";
    
  • बस टाइपिंग std ::

    std::cout << "Values:";
    

एक और कारण आश्चर्य है।

अगर मैं cout << blah , std::cout << blah बजाय देखता हूं

मुझे लगता है कि यह cout क्या है? क्या यह सामान्य cout ? क्या यह कुछ खास है?


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

template <typename FloatType> inline
FloatType compute_something(FloatType x)
{
    using namespace std; //no problem since scope is limited
    return exp(x) * (sin(x) - cos(x * 2) + sin(x * 3) - cos(x * 4));
}

यह स्पष्ट योग्यता ( std::sin , std::cos ...) से बेहतर है क्योंकि यह छोटा है और इसमें उपयोगकर्ता परिभाषित फ़्लोटिंग पॉइंट प्रकारों (तर्क आश्रित लुकअप के माध्यम से) के साथ काम करने की क्षमता है।


कोड देखना अच्छा लगता है और पता है कि यह क्या करता है। अगर मैं std::cout देखता हूं तो मुझे पता है कि यह std लाइब्रेरी का cout स्ट्रीम है। अगर मैं cout देखता हूं तो मुझे नहीं पता। यह std पुस्तकालय की cout धारा हो सकती है। या एक int cout = 0; हो सकता है int cout = 0; एक ही समारोह में दस लाइनें अधिक होती हैं। या उस फ़ाइल में cout नामक एक static चर। यह कुछ भी हो सकता है।

अब एक लाख लाइन कोड बेस लें, जो विशेष रूप से बड़ा नहीं है, और आप एक बग खोज रहे हैं, जिसका अर्थ है कि आप जानते हैं कि इस दस लाख लाइनों में एक पंक्ति है जो ऐसा नहीं करती है जो ऐसा करने के लिए किया जाता है। cout << 1; एक static int नामक cout पढ़ सकता है, इसे बाईं ओर एक तरफ स्थानांतरित कर सकता है, और परिणाम निकाल सकता है। एक बग की तलाश में, मुझे यह जांचना होगा। क्या आप देख सकते हैं कि मैं वास्तव में std::cout को देखना पसंद करता हूं?

यह उन चीजों में से एक है जो वास्तव में एक अच्छा विचार प्रतीत होता है यदि आप एक शिक्षक हैं और कभी भी जीवित रहने के लिए किसी भी कोड को लिखना और बनाए रखना नहीं था। मुझे कोड देखने से प्यार है (1) मुझे पता है कि यह क्या करता है; और, (2) मुझे विश्वास है कि इसे लिखने वाला व्यक्ति जानता था कि यह क्या करता है।


मैं इसे एक बुरा अभ्यास भी मानता हूं। क्यूं कर? सिर्फ एक दिन मैंने सोचा कि नामस्थान का कार्य सामान को विभाजित करना है, इसलिए मुझे इसे सब कुछ एक वैश्विक बैग में फेंकने से खराब नहीं करना चाहिए। हालांकि, अगर मैं अक्सर 'cout' और 'cin' using std::cout; using std::cin; हूं, तो मैं लिखता हूं: using std::cout; using std::cin; using std::cout; using std::cin; सीपीपी फ़ाइल में (कभी भी हेडर फ़ाइल में नहीं है क्योंकि यह #include अंतर्निहित के साथ प्रचारित करता है)। मुझे लगता है कि कोई भी cin कभी भी धारावाहिक या cin का नाम नहीं रखेगा। ;)


मैं मानता हूं कि इसे वैश्विक रूप से उपयोग नहीं किया जाना चाहिए, लेकिन namespace में स्थानीय रूप से उपयोग करना इतना बुरा नहीं है। "सी ++ प्रोग्रामिंग भाषा" से एक उदाहरण यहां दिया गया है:

namespace My_lib {

    using namespace His_lib; // everything from His_lib
    using namespace Her_lib; // everything from Her_lib

    using His_lib::String; // resolve potential clash in favor of His_lib
    using Her_lib::Vector; // resolve potential clash in favor of Her_lib

}

इस उदाहरण में, हमने संभावित संरचना संघर्ष और उनकी रचना से उत्पन्न होने वाली अस्पष्टताओं का समाधान किया।

नाम स्पष्ट रूप से घोषित किए गए हैं ( His_lib::String उपयोग करके घोषित नामों सहित घोषित किया गया His_lib::String ) एक प्रयोग-निर्देश ( using namespace Her_lib ) द्वारा किसी अन्य दायरे में सुलभ किए गए नामों पर प्राथमिकता लेते हैं।


यदि आप दायां हेडर फाइल आयात करते हैं तो अचानक आपके पास hex , left , plus या आपके वैश्विक दायरे में count है। यह आश्चर्यजनक हो सकता है अगर आपको पता नहीं है कि std:: में इन नाम हैं। यदि आप स्थानीय रूप से इन नामों का उपयोग करने का भी प्रयास करते हैं तो यह काफी भ्रम पैदा कर सकता है।

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


यह जटिलता के प्रबंधन के बारे में सब कुछ है। नेमस्पेस का उपयोग करना उन चीजों को खींच देगा जो आप नहीं चाहते हैं, और इस प्रकार संभवतः इसे डीबग करना मुश्किल हो जाता है (मैं संभवतः कहता हूं)। सभी जगहों पर std :: का उपयोग करना कठिन है (अधिक पाठ और वह सब)।

पाठ्यक्रमों के लिए घोड़े - अपनी जटिलता का प्रबंधन करें कि आप कैसे कर सकते हैं और सक्षम महसूस कर सकते हैं।


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

सारांश

नेमस्पेस उपयोग आपकी सुविधा के लिए हैं, न कि आप दूसरों पर आक्रमण करने के लिए: किसी भी अंतर्निहित घोषणा या # अंतर्निहित निर्देश से पहले एक उपयोग निर्देश लिखना कभी नहीं लिखें।

अनुशासनिक: शीर्षलेख फ़ाइलों में, निर्देशों का उपयोग करके या घोषणाओं का उपयोग करके नामस्थान-स्तर नहीं लिखें; इसके बजाय, स्पष्ट रूप से नामस्थान-सभी नामों को अर्हता प्राप्त करें। (दूसरा नियम पहले से आता है, क्योंकि शीर्षलेख कभी नहीं जानते कि अन्य शीर्षलेख # उनके बाद क्या दिखाई दे सकता है।)

विचार-विमर्श

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


एक उदाहरण जहां नामस्थान std का उपयोग गिनती की अस्पष्टता के कारण जटिलता त्रुटि को फेंकता है, जो एल्गोरिदम लाइब्रेरी में भी एक फ़ंक्शन है।

#include <iostream>

using namespace std;

int count = 1;
int main() {
    cout<<count<<endl;
}

विचार करें

// myHeader.h
#include <sstream>
using namespace std;


// someoneElses.cpp/h
#include "myHeader.h"

class stringstream {  // uh oh
};

ध्यान दें कि यह एक साधारण उदाहरण है, यदि आपके पास 20 फाइलों के साथ फाइलें हैं और अन्य आयात आपके पास समस्या का पता लगाने के लिए निर्भरता का एक टन होगा। इसके बारे में बदतर बात यह है कि आप संघर्ष की परिभाषाओं के आधार पर अन्य मॉड्यूल में असंबंधित त्रुटियां प्राप्त कर सकते हैं।

यह भयानक नहीं है लेकिन आप हेडर फाइलों या वैश्विक नेमस्पेस में इसका उपयोग न करके अपने आप को सिरदर्द बचाएंगे। शायद यह बहुत सीमित क्षेत्रों में ऐसा करने के लिए ठीक है, लेकिन मुझे यह स्पष्ट करने के लिए अतिरिक्त 5 वर्ण टाइप करने में कोई समस्या नहीं हुई है कि मेरे कार्य कहां से आ रहे हैं।


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

मेरा मतलब वास्तव में ... कह रहा है "इस उपस्थित होने पर भरोसा न करें" बस आपको इस पर भरोसा करने के लिए स्थापित कर रहा है कि वह उपस्थित न हो। आपको लगातार कोड स्निपेट उधार लेने और लगातार मरम्मत करने के मुद्दे होने जा रहे हैं। बस अपने उपयोगकर्ता द्वारा परिभाषित और उधारित सामान को सीमित दायरे में रखें क्योंकि वे होना चाहिए और ग्लोबल्स के साथ बहुत कम होना चाहिए (ईमानदारी से ग्लोबल्स को हमेशा "संकलन, बाद में संवेदना" के उद्देश्यों के लिए अंतिम उपाय होना चाहिए)। वास्तव में मुझे लगता है कि यह आपके शिक्षक से बुरी सलाह है क्योंकि std का उपयोग "cout" और "std :: cout" दोनों के लिए काम करेगा, लेकिन std का उपयोग न केवल "std :: cout" के लिए काम करेगा। आप अपने सभी कोड लिखने के लिए हमेशा भाग्यशाली नहीं होंगे।

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


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

namespace Mylib{
    template<class T> class Stack{ /* ... */ };
    / / ...
}
namespace Yourlib{
    class Stack{ /* ... */ };
    / / ...
}
void f(int max) {
    Mylib: :Stack<int> s1(max) ; / / use my stack
    Yourlib: :Stack s2(max) ; / / use your stack
    / / ...
}

नामस्थान नाम दोहराएं पाठकों और लेखकों दोनों के लिए एक व्याकुलता हो सकती है। नतीजतन, यह कहना संभव है कि किसी विशेष नामस्थान से नाम स्पष्ट योग्यता के बिना उपलब्ध हैं। उदाहरण के लिए:

void f(int max) {
    using namespace Mylib; / / make names from Mylib accessible
    Stack<int> s1(max) ; / / use my stack
    Yourlib: :Stack s2(max) ; / / use your stack
    / / ...
}

नेमस्पेस विभिन्न पुस्तकालयों और कोड के विभिन्न संस्करणों के प्रबंधन के लिए एक शक्तिशाली उपकरण प्रदान करते हैं। विशेष रूप से, वे प्रोग्रामर विकल्प प्रदान करते हैं कि गैर-लोकल नाम का संदर्भ कैसे स्पष्ट किया जाए।

स्रोत: Bjarne Stroustrup द्वारा सी ++ प्रोग्रामिंग भाषा का अवलोकन


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

namespace foo {
    void a(float) { /* does something */ }
}

namespace bar {
    ...
}

अब मान लीजिए कि आप अपने कार्यक्रम में फू और बार का एक साथ उपयोग करते हैं:

using namespace foo;
using namespace bar;

void main() {
    a(42);
}

इस बिंदु पर सबकुछ ठीक है। जब आप अपना प्रोग्राम चलाते हैं तो यह 'कुछ करता है'। लेकिन बाद में आप बार को अपडेट करते हैं और मान लें कि यह इस तरह बदल गया है:

namespace bar {
    void a(float) { /* does something completely different */ }
}

इस बिंदु पर आपको एक कंपाइलर त्रुटि मिलेगी:

using namespace foo;
using namespace bar;

void main() {
    a(42);  // error: call to 'a' is ambiguous, should be foo::a(42)
}

तो आपको यह समझाने के लिए कुछ रखरखाव करने की आवश्यकता होगी कि 'ए' जिसका मतलब है (यानी foo::a)। यह शायद अवांछित है, लेकिन सौभाग्य से यह बहुत आसान है (बस foo::सभी कॉल के सामने जोड़ें aकि संकलक के रूप में संकलक चिह्न)।

लेकिन एक वैकल्पिक परिदृश्य की कल्पना करें जहां बदले में इसके बदले में बार बदल दिया गया है:

namespace bar {
    void a(int) { /* does something completely different */ }
}

इस बिंदु पर a(42)अचानक कॉल करने के bar::aबजाए foo::aऔर कुछ 'करने' के बजाय आपकी कॉल अचानक 'कुछ अलग' होती है। कोई संकलक चेतावनी या कुछ भी नहीं। आपका कार्यक्रम चुपचाप कुछ पहले से अलग कुछ अलग करना शुरू कर देता है।

जब आप किसी नामस्थान का उपयोग करते हैं तो आप इस तरह के परिदृश्य को जोखिम दे रहे हैं, यही कारण है कि लोग नामस्थानों का उपयोग करके असहज हैं। नामस्थान में जितनी अधिक चीजें संघर्ष का जोखिम अधिक होती हैं, इसलिए अन्य नामस्थानों की तुलना में लोग नेमस्पेस std (उस नामस्थान में चीज़ों की संख्या के कारण) का उपयोग करके और भी असहज हो सकते हैं।

आखिरकार यह लेखन योग्यता बनाम विश्वसनीयता / रखरखाव के बीच एक व्यापार-बंद है। पठनीयता भी कारक हो सकती है, लेकिन मैं किसी भी तरह से जाने के लिए तर्क देख सकता था। आम तौर पर मैं कहूंगा कि विश्वसनीयता और रखरखाव अधिक महत्वपूर्ण है, लेकिन इस मामले में आप लगातार दुर्लभ विश्वसनीयता / रखरखाव प्रभाव के लिए उत्तरदायित्व लागत का भुगतान करेंगे। 'सर्वश्रेष्ठ' व्यापार-बंद आपकी परियोजना और आपकी प्राथमिकताओं पर निर्धारित होगा।


मुझे नहीं लगता कि यह सभी परिस्थितियों में आवश्यक रूप से खराब अभ्यास है, लेकिन जब आप इसका इस्तेमाल करते हैं तो आपको सावधान रहना होगा। यदि आप लाइब्रेरी लिख रहे हैं, तो संभवतः आपको अपनी लाइब्रेरी को अन्य पुस्तकालयों के साथ सिर डालने से रोकने के लिए नामस्थान के साथ स्कोप रिज़ॉल्यूशन ऑपरेटर का उपयोग करना चाहिए। आवेदन स्तर कोड के लिए, मुझे इसके साथ कुछ भी गलत नहीं दिख रहा है।


मेरे अनुभवों से, यदि आपके पास कई पुस्तकालय हैं जो कहते हैं cout, लेकिन एक अलग उद्देश्य के लिए आप गलत का उपयोग कर सकते हैं cout

उदाहरण के लिए, यदि मैं टाइप करता हूं, using namespace std;और using namespace otherlib;टाइप std::cout(या 'otherlib::cout') के बजाय केवल cout (जो दोनों में होता है) टाइप करता है , तो आप गलत का उपयोग कर सकते हैं और त्रुटियां प्राप्त कर सकते हैं, यह उपयोग करने के लिए और अधिक प्रभावी और कुशल है std::cout


यह आपके सॉफ़्टवेयर या प्रोजेक्ट प्रदर्शन को और खराब नहीं करता है, आपके स्रोत कोड की शुरुआत में नामस्थान को शामिल करना बुरा नहीं है। using namespace stdनिर्देशों को शामिल करना आपकी आवश्यकताओं और जिस तरह से आप सॉफ्टवेयर या प्रोजेक्ट विकसित कर रहे हैं उसके अनुसार भिन्न होता है।

namespace stdसी ++ मानक कार्य करता है और चर होते हैं। यह नेमस्पेस उपयोगी होता है जब आप अक्सर सी ++ मानक फ़ंक्शंस का उपयोग करेंगे।

जैसा कि इस page में उल्लेख किया गया है :

नेमस्पेस std का उपयोग कर बयान आम तौर पर खराब अभ्यास माना जाता है। इस कथन का विकल्प उस नामस्थान को निर्दिष्ट करना है जिस पर पहचानकर्ता स्कोप ऑपरेटर (: :) का उपयोग कर रहा है जब भी हम एक प्रकार घोषित करते हैं।

और यह राय देखें :

जब आप नामस्थान का भारी उपयोग करते हैं और यह सुनिश्चित करने के लिए कि कुछ भी टकरा नहीं जाएगा, तो अपनी स्रोत फ़ाइल में "नेमस्पेस std का उपयोग करके" कोई समस्या नहीं है।

कुछ लोगों ने कहा था कि using namespace stdआपकी स्रोत फ़ाइलों में शामिल करने का एक बुरा अभ्यास है क्योंकि आप उस नामस्थान से सभी कार्यों और चरों से आक्रमण कर रहे हैं। जब आप एक ही नाम के साथ एक नया फ़ंक्शन परिभाषित करना चाहते हैं, तो आपके द्वारा निहित किसी अन्य फ़ंक्शन namespace stdमें फ़ंक्शन अधिभारित होगा और यह संकलन या निष्पादन के कारण समस्याएं उत्पन्न कर सकता है। जैसा कि आप उम्मीद करते हैं यह संकलन या निष्पादन नहीं करेगा।

जैसा कि इस page में उल्लेख किया गया है :

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

...

अब विकास के बाद के चरण में, हम cout के एक और संस्करण का उपयोग करना चाहते हैं जो कि "foo" नामक कुछ लाइब्रेरी में लागू किया गया है (उदाहरण के लिए)

...

ध्यान दें कि एक अस्पष्टता कैसे है, जिस पर लाइब्रेरी cout इंगित करता है? कंपाइलर इसका पता लगा सकता है और प्रोग्राम संकलित नहीं कर सकता है। सबसे बुरे मामले में, प्रोग्राम अभी भी संकलित हो सकता है लेकिन गलत फ़ंक्शन को कॉल कर सकता है, क्योंकि हमने कभी निर्दिष्ट नहीं किया कि पहचानकर्ता किस नामस्थान से संबंधित है।


यह इस बात पर निर्भर करता है कि यह कहां स्थित है। यदि यह एक सामान्य शीर्षलेख है, तो आप इसे नामस्थान के मान को वैश्विक नामस्थान में विलय करके कम कर रहे हैं। ध्यान रखें, यह मॉड्यूल ग्लोबल्स बनाने का एक साफ तरीका हो सकता है।





c++-faq