Is there any good reason why C++ namespaces are "closed" in D?

Walter Bright newshound2 at digitalmars.com
Wed Aug 1 23:04:01 UTC 2018


On 8/1/2018 10:24 AM, Jonathan M Davis wrote:
> Not to say that that can't work, but I have to say that it seems pretty ugly
> if using extern(C++, NS) requires a bunch of aliases just to use symbols
> normally.

What is normal is a slippery concept, especially when one is comparing different 
lookup rules between languages. D modules do not a 1:1 correspondence with C++ 
namespaces, either (not even close).

Aliases are a normal and highly useful D tool to copy names from one scope to 
another.


> Certainly, it does come across like
> you didn't trust the D module system to do its job for some reason.

Reorganizing the code into modules means potentially forcing users to split code 
from one C++ file into multiple D files. How's that really going to work if you 
have a translation tool? One of the aspects of Java I didn't care for was 
forcing each class into its own file.

So while Manu is clearly happy with cutting up a C++ file into multiple D files, 
I doubt that is universal. His proposal would pretty much require that for 
anyone trying to work with C++ namespaces who ever has a name collision/hijack 
or wants to make the code robust against collision/hijacking.

An example of silent hijacking:

    extern (C++, "ab") void foo(long); // original code
    ... lots of code ...
    extern (C++, "cd") void foo(int); // added later by intern, should have been
                                      // placed in another module
    ... a thousand lines later ...
    foo(0); // OOPS! now calling cd.foo() rather than ab.foo(), D sux

You might say "nobody would ever write code like that." But that's like the C 
folks saying real C programmers won't write:

     int a[10];
     for (int i = 0; i <= 10; ++i)
        ...a[i]...

But we both know they do just often enough for it to be a disaster.

Now, with D:

     extern (C++, ab) void foo(long);
     foo(0);    // works!
     ---
     extern (C++, ab) void foo(long);
     extern (C++, ab) void foo(int);   // error!
     ---
     extern (C++, ab) void foo(long);
     extern (C++, cd) void foo(int);
     foo(0);    // error!

I juxtaposed the lines so it's obvious. It's not so obvious when there's a 
thousand lines of code between each of those lines. It's even worse when 
foo(long) sends a birthday card to your daughter, and foo(int) launches nuclear 
missiles.

Yes, this extra protection comes at a cost - you'll have to type a bit more. 
Just like D doesn't allow implicit declaration of variables, requires static 
typing, and variables are always initialized unless you explicitly use `= void`. 
The protection is worth it, and is part of D's philosophy.

I hope that adequately answers the "for some reason" :-)


More information about the Digitalmars-d mailing list