Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C++ Namespaces, comparison to Java packages

I've done a bunch of Java coding recently and have got used to very specific package naming systems, with deep nesting e.g. com.company.project.db. This works fine in Java, AS3/Flex and C#. I've seen the same paradigm applied in C++ too, but I've also heard that it's bad to view C++ namespaces as direct counterparts to Java packages.

Is that true, and why? How are namespaces/packages alike and different? What problems are likely to be seen if you do use deep nested namespaces?

like image 557
Mr. Boy Avatar asked Jan 21 '10 09:01

Mr. Boy


People also ask

What is C namespace equivalent in Java?

There's no such term as "namespace" in Java - a package acts as a namespace in Java though, in terms of providing a scope for names. It's also part of the accessibility model. From section 7 of the Java Language Specification: Programs are organized as sets of packages.

Is C# namespace same as Java package?

The main difference between namespace and package is that namespace is available in C# (. NET) to organize the classes so that it is easier to handle the application, while package is available in Java and groups similar type of classes and interfaces to improve code maintainability.

Is namespace same as package?

Packages are used in Java in order to prevent naming conflicts, to control access, to make searching/locating and usage of classes, interfaces, enumerations and annotations easier, etc. A namespace is designed for providing a way to keep one set of names separate from another.

Is namespace in C++ similar to package in Java?

C++ namespaces are the rough equivalents of Java packages and serve the same purpose. To create a namespace and put some items in the namespace you use a namespace declaration. Since we are mostly going to be writing small programs in this course we won't need to create namespaces frequently.


3 Answers

In C++ namespaces are just about partitioning the available names. Java packages are about modules. The naming hierarchy is just one aspect of it.

There's nothing wrong, per-se, with deeply nested namespaces in C++, except that they're not normally necessary as there's no module system behind them, and the extra layers just add noise. It's usually sufficient to have one or two levels of namespace, with the odd extra level for internal details (often just called Details).

There are also extra rules to C++ namespaces that may catch you out if overused - such as argument-dependent-lookup, and the rules around resolving to parent levels. WRT the latter, take:

namespace a{ namespace b{ int x; } }
namespace b{ string x; }
namespace a
{
  b::x = 42;
}

Is this legal? Is it obvious what's happening? You need to know the precendence of the namespace resolution to answer those questions.

like image 180
philsquared Avatar answered Oct 02 '22 21:10

philsquared


Java packages are not nested, they're flat. Any apparent nesting is nothing more than a naming convention.

For example, the package com.company.project.db has no relation whatsoever to com.company.project or com.company.project.db.x. Code in com.company.project.db has no more access to code in com.company.project.db.x than would code in a.b.c.

like image 29
skaffman Avatar answered Oct 02 '22 21:10

skaffman


Here are some reasons why and how C++ namespaces are different than Java or C# namespaces.

Avoiding conflicts

In Java/C# languages, namespaces are intended to avoid conflicts between names in different parts of class libraries. You may have class called "Watcher" in 5 different places in namespace hierarchy in C#. In C++, if you have same named classes occurring in your library then you put inside another class instead of creating namespaces. Such nested classes are all fine and encouraged and in fact the syntax also treats as if class is a namespace using :: operator.

How much nested namespaces should be?

Popular libraries like Boost, Eigen and of course, STL provides good examples. these libraries typically have pretty much everything stuffed in to one namespace like std:: or boost:: or eigen::. Few components get their own namespace like std::ios or boost:filesystem. There is no consistent rules around when to use second level but it seems large or separately developed/maintained or optional components typically get their own namespaces. The third level is even more rare. Generally I use the structure company::project and for large independently usable subsystem of projects company::project::component.

Avoiding conflicts in external libraries

Now the big question: What if you get two libraries from two different people which has exact same namespaces and classes? This situation is fairly rare because most people tend to wrap their libraries at least in their project's name. Even if project names are same, its even rarer that you end up using libraries from both. However sometimes bad decisions are made for project names (ahm... "metro", "apollo" ...) or even namespaces are just not used at all. If that happens, you wrap #include for either or both libraries in to a namespace and conflict is resolved! This is one reason why people don't bother too much about conflicts because resolving them is trivial. If you follow the practice of using company::project then conflicts become super rare.

Differences in languages

Although C++ provides using namespace statement just like C#, its generally considered a bad practice to "import" everything in your own namespace. The reason for this is that a header can contain lots of "bad" stuff including redefining things that can totally surprise you. This is quite unlike C#/Java where you only get clean public interface when you do equivalent of using namespace. (side note: in C++ you can achieve the same thing by using Pimpl pattern but its usually too much of extra plumbing and few libraries actually do it). So you almost never want to do using namespace. Instead you do typedefs (or using name =) for what you actually want to use. This again makes deeply nested namespaces impractical to use.

Organizing code

In Java/C#, people tend to organize code in folders a lot. Typically as folder grows more than 20 or even 10 files, people would start thinking about folders. In C++, things are more diverse but for many large projects flatter directory structures are preferred. For example, standard library's std folder has 53 files and Facebook's folly project seems to go same route. I think one reason for this probably is the fact Java/C# folks use visual IDEs more and use mouse scrolls in folder navigation as opposed to console where you can use wild cards to find file in flat structure. Also C++ programmers absolutely don't shy away from putting multiple classes in single file and naming file as logical unit instead of same as class name unlike in C# or Java. This makes compilation faster which is very important for large projects. While there is no language-level requirement for having its own namespace for each folder many C++ developers prefers to assign its own namespace to each folder and keep folder hierarchy 2 or less levels deep.

Possible exception

In C++ you can refer to A::B::C::D as just C::D if you are already inside A::B. So if you have private code or less used classes that you want to push further down then you might do so while still keeping your own relative depth to 2 or so. In this case, you might also want to create folder for each level just so file locations are predictable. In general, there are no gold standards in this area but you do not want to go overboard with deeply nested namespaces mimicking C#/Java.

Related

  • Avoiding collisions in header files; use a namespace wrapper?

  • Is there a 'right' way to approach namespaces in C++

  • Using fully qualified names in C++

  • Java packages vs. C++ libraries

  • Is there a better way to express nested namespaces in C++ within the header

  • How do you properly use namespaces in C++?

like image 39
Shital Shah Avatar answered Oct 01 '22 21:10

Shital Shah