Warum Namespace Std?
C++ verfügt über eine Standardbibliothek, die gängige Funktionen wie Container, Algorithmen usw. enthält, die Sie beim Erstellen Ihrer Anwendungen verwenden. Wenn die von diesen verwendeten Namen offengelegt würden, z. B. wenn eine Warteschlangenklasse global definiert würde, könnte man denselben Namen nie wieder ohne Konflikte verwenden. Daher wurde ein Namensraum, std, geschaffen, um diese Änderung aufzunehmen.
Grund 1 für die Nichtverwendung: Schlechte Praxis
Die Anweisung, den Namespace std zu verwenden, wird allgemein als schlechte Praxis angesehen. Die Alternative zu dieser Anweisung besteht darin, den Namespace, zu dem der Bezeichner gehört, bei jeder Deklaration eines Typs mit dem Scope-Operator(::) anzugeben. Diese Anweisung erspart uns zwar die Eingabe von std::, wenn wir auf eine Klasse oder einen Typ zugreifen wollen, der im std-Namensraum definiert ist, importiert aber den gesamten std-Namensraum in den aktuellen Namensraum des Programms.
Grund 2 für die Nichtverwendung: Compiler gerät durcheinander
Es ist in Ordnung, die gesamte std-Bibliothek in Spielzeugprogrammen zu importieren, aber in produktionsfähigem Code ist es schlecht. using namespace std; macht jedes Symbol, das im Namensraum std deklariert ist, ohne den Namespace-Qualifizierer zugänglich.
Zum Beispiel:
Nehmen wir nun an, Sie aktualisieren auf eine neuere Version von C++, und es werden weitere neue std-Namespace-Symbole in Ihr Programm eingefügt, von denen Sie keine Ahnung haben. Möglicherweise haben Sie diese Symbole bereits in Ihrem Programm verwendet. Nun wird der Compiler Schwierigkeiten haben, herauszufinden, ob das deklarierte Symbol zu Ihrer eigenen Implementierung gehört oder aus dem Namespace stammt, den Sie ohne jede Ahnung importiert haben. Manche Compiler geben Fehler aus. Wenn Sie Pech haben, wählt der Compiler die falsche Implementierung und kompiliert sie, was mit Sicherheit zu Laufzeitabstürzen führt.
Effekt der Namensraumverschmutzung:
Während diese Praxis für Beispielcode in Ordnung ist, ist es nicht gut, den gesamten std-Namespace in den globalen Namespace zu ziehen, da dies den Zweck von Namespaces unterläuft und zu Namenskollisionen führen kann. Diese Situation wird als Namespace Pollution bezeichnet.
710 Stimmen
Vergessen Sie nicht, was Sie tun können: "using std::cout;", was bedeutet, dass Sie nicht std::cout eingeben müssen, aber nicht gleichzeitig den gesamten std-Namensraum mit einbeziehen.
115 Stimmen
Es ist besonders schlecht, 'using namespace std' in Headerdateien im Dateisystem zu verwenden. Die Verwendung in Quelldateien (*.cpp) im Dateisystem nach allen Includes ist nicht ganz so schlimm, da ihre Wirkung auf eine einzige Übersetzungseinheit beschränkt ist. Noch weniger problematisch ist die Verwendung innerhalb von Funktionen oder Klassen, da die Wirkung auf den Funktions- oder Klassenbereich beschränkt ist.
15 Stimmen
Ich würde davon abraten, die using-Direktive zu verwenden, aber für bestimmte Namespaces wie
std::literals::chrono_literals
,Poco::Data:Keywords
,Poco::Units
und andere Dinge, die mit Literalen oder Lesbarkeitstricks zu tun haben. Immer dann, wenn es in Header- oder Implementierungsdateien steht. In einem Funktionsbereich mag es in Ordnung sein, aber abgesehen von Literalen und anderen Dingen ist es nicht nützlich.1 Stimmen
@sh- Warum meinen Sie, dass es "besonders schlecht" ist, "using namespace std" zu verwenden?
22 Stimmen
@Jon: Es hat nichts mit dem Namespace std im Besonderen zu tun. Meine Betonung lag auf "in Dateigröße in Header-Dateien". Um es als Ratschlag zu formulieren: Verwenden Sie "using namespace" (std oder andere) nicht im Dateisystem von Header-Dateien. Es ist OK, es in Implementierungsdateien zu verwenden. Entschuldigung für die Zweideutigkeit.
11 Stimmen
Es wird nur in Kopfzeilen als schlechte Praxis angesehen. In Quelldateien, die nicht anderweitig eingebunden sind (z. B. cpp-Dateien), ist es in Ordnung. Siehe @mattnewport 's Antwort unten. stackoverflow.com/a/26722134/125997
3 Stimmen
Ich habe den anderen keine Antwort hinzuzufügen, aber ich benutze:
using [namespace]::[identifier];
im lokalen Bereich von relativ einfachen Quelldateien. Wenn ich zum Beispiel einen Header habe, der häufig die voll qualifizierte:std::size_t
Typ, werde ich normalerweise vorangestellt:using std::size_t;
zur Umsetzung. Dies vereinfacht Lesen den Code und wirkt sich nur auf den lokalen Bereich aus - das heißt:using std::[identifier];
verwendet die Prinzip der geringsten Überraschung . Es gibt zu viele Bezeichner in derstd
Namespace, den man im Auge behalten muss. Spätere C++-Revisionen können Bezeichner hinzufügen, die mit Ihren eigenen kollidieren!0 Stimmen
Das macht Ihren Code einfacher.
0 Stimmen
>Warum ist das so? Weil die Leute in manchen Bereichen nichts wirklich zu tun haben und anfangen, über Dinge zu debattieren, die nicht wichtig sind. In der Sprache C++ können Sie jede Strategie verwenden, aber bitte verstehen Sie die using-directive und die using-declaration.