Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why and how should I use namespaces in C++?

Tags:

c++

namespaces

I have never used namespaces for my code before. (Other than for using STL functions)

  1. Other than for avoiding name conflicts, is there any other reason to use namespaces?
  2. Do I have to enclose both declarations and definitions in namespace scope?
like image 867
nakiya Avatar asked Nov 18 '10 05:11

nakiya


People also ask

Why do we use namespace in C?

The namespace keyword is used to declare a scope that contains a set of related objects. You can use a namespace to organize code elements and to create globally unique types.

How do you use namespaces correctly?

MyNamespace::MyClass* pClass = new MyNamespace::MyClass(); Or, if you want to always use a specific namespace, you can do this: using namespace MyNamespace; MyClass* pClass = new MyClass();

Do I need to use namespaces?

Under no circumstances must you use namespace std within a header file, that's a recipe for errors straight away. Do use namespaces, they will make your code so much more sorted out. And finally if you're going to use namespace STD, don't write functions that have the same name to functions within the standard library.

Should you use namespace CPP?

A namespace defines a new scope. They provide a way to avoid name collisions. Namespaces in C++ are most often used to avoid naming collisions. Although namespaces are used extensively in recent C++ code, most older code does not use this facility.


1 Answers

One reason that's often overlooked is that simply by changing a single line of code to select one namespaces over another you can select an alternative set of functions/variables/types/constants - such as another version of a protocol, or single-threaded versus multi-threaded support, OS support for platform X or Y - compile and run. The same kind of effect might be achieved by including a header with different declarations, or with #defines and #ifdefs, but that crudely affects the entire translation unit and if linking different versions you can get undefined behaviour. With namespaces, you can make selections via using namespace that only apply within the active namespace, or do so via a namespace alias so they only apply where that alias is used, but they're actually resolved to distinct linker symbols so can be combined without undefined behaviour. This can be used in a way similar to template policies, but the effect is more implicit, automatic and pervasive - a very powerful language feature.


UPDATE: addressing marcv81's comment...

Why not use an interface with two implementations?

"interface + implementations" is conceptually what choosing a namespace to alias above is doing, but if you mean specifically runtime polymorphism and virtual dispatch:

  • the resultant library or executable doesn't need to contain all implementations and constantly direct calls to the selected one at runtime

  • as one implementation's incorporated the compiler can use myriad optimisations including inlining, dead code elimination, and constants differing between the "implementations" can be used for e.g. sizes of arrays - allowing automatic memory allocation instead of slower dynamic allocation

  • different namespaces have to support the same semantics of usage, but aren't bound to support the exact same set of function signatures as is the case for virtual dispatch

  • with namespaces you can supply custom non-member functions and templates: that's impossible with virtual dispatch (and non-member functions help with symmetric operator overloading - e.g. supporting 22 + my_type as well as my_type + 22)

  • different namespaces can specify different types to be used for certain purposes (e.g. a hash function might return a 32 bit value in one namespace, but a 64 bit value in another), but a virtual interface needs to have unifying static types, which means clumsy and high-overhead indirection like boost::any or boost::variant or a worst case selection where high-order bits are sometimes meaningless

  • virtual dispatch often involves compromises between fat interfaces and clumsy error handling: with namespaces there's the option to simply not provide functionality in namespaces where it makes no sense, giving a compile-time enforcement of necessary client porting effort

like image 93
Tony Delroy Avatar answered Sep 19 '22 14:09

Tony Delroy