On Friday, 3 August 2018 at 21:20:37 UTC, Walter Bright wrote:
On 8/2/2018 2:26 AM, Daniel N wrote:
Personally I would never *bind* to two different namespaces in a single file,

You'd be amazed at what people do and then set their entire store based on it. If the language spec allows it, people will do it. People will even design their code to require certain bugs in the compiler. (This really blows when you're trying to write a standard compliant C/C++ compiler and you get angry letters from customers about why I'm not supporting some stupid bug in BrandX C++ that they rely on.)

One of my favorite stories about this was a company that had a coding style where their comments looked like this:

    //******** text ********\\

    int x;

They thought it was marvelous! But what really happens when you've got two line concatenation characters at the end? Is one line concatenated, or two? You have to carefully read the spec to determine which, and it matters because if two are concatenated then the declaration of x vanishes. And BrandX did it wrong, the customer wrote all their code this way, and it all broke with my compiler, and of course it was all my fault.

I thought "who in their right mind would write code that way?" At least I could justify myself with BrandX is a buggy compiler, but when the behavior is in the spec, I have no leg to stand on.

A simple regex could have fixed that problem. They dug themselves a hole and if they don't want to support other compiles, then they will be stuck with BrandX.

If we want to support interfacing with C++, we have to support badly written C++, because that is the NORMAL case. Telling them their code is **** and that they should rewrite it in order to work with D is never, ever going to work.

There seems to be a misunderstanding here, you don't have to rewrite the C++ code. Merely the D code has to be formatted differently. Unless you have some obsession with maintaining 1:1 C++ and D code. Which is not a technical problem, but one of organization. D isn't C++ and trying to do something crazy like make it compatible so that the files are 1:1 is crazy and unachievable. It only causes problems like what we have now. Maintaining a 1:1 correlation isn't on most D users that work with C++ wish list. Hell all of the Derelict libraries don't maintain a 1:1 at all.

Another anecdote - Microsoft MASM in the 80's was full of bugs. I mean full of bugs. When Borland came out with an assembler, it wouldn't work with most of the ASM files out there. They finally had to engineer in what they called "quirks mode" to emulate MASM's bugs. Telling customers to rework their ASM files didn't work for a large company, either.

The difference is they would have to rework their existing code. If you are writing D source code bindings for your code, then you are essentially writing new code. You don't have to worry about backwards compatibility.

Not only that, who do you think even writes bindings for libraries? Most bindings are done by the community for libraries to other languages. How many companies do you know have bindings for their C/C++ libraries for D, that maintains them?

are there any other additional benefits to the current design which I'm overlooking?

With a non-scoped extern(c++) we could simply use two files.

Yes. But then you'll have the people who want a 1:1 correspondence with their C++ files and the corresponding D files. I happen to be one of those people, for the ease of maintaining a translation (and for comparing it with the original C++ source code if it is not behaving correctly).

Besides, I provided solutions for both Manu's case and Atila's (they are different), which are easier than "simply" breaking things up into multiple files.

So why can't you define the same namespace twice in the same module? There was some conflict that didn't allow it to be implemented the same way as in C++ or something right. So why try to imitate C++ in D but fail to do so because D isn't C++. I think it's worse to try to imitate namespaces in D then create these exceptions to rules when you get snagged on a limitation.

Imagine someone tried to write a DIP to add namespaces into D. Do you think anything like that would ever be accepted? God damn hell no. That's what modules are for. So why are you trying to implement namespaces in D under the guise of C++ name mangling. What extern(C++) should be used for is allowing you to call C++ code from D, not to be able to format C++ code into D. The only problem you have with breaking code up into multiple files is that it isn't 1:1. That's not a technical problem, it's a problem of conflicting personal opinion. If it's not 1:1, who cares? If some some odd reason you have two namespaces in one file in C++, odds are they are probably separated in that one file anyway. If not and for some reason the the code has multiple namespace definitions smashed together into one file, flip-floping between namespaces. That's not D's problem to fix the project's poor organization method. Modules are a better way of doing things, we shouldn't be promoting C++'s mistakes in D.


My conclusion is that _if_ I understood you correctly, it must mean that in the examples which you have in mind, it is common to *bind* to two namespaces in the same file? Could you give a real-world examples of two namespaces which you would like to mix like that in the same *bindings* file? Is it for instance 'std' and 'std::experimental'?

In D it is not allowed to have multiple modules in the same file. This can become deeply entrenched in the way one thinks about programming, to the point where one cannot conceive of doing it other ways, i.e. ways that C++ allows, and that I believe are poor practice, but people do anyway.

You can see this in the C++ backend. It is certainly not organized in a module-like manner. (It predates C++ namespaces, so doesn't use them.)


On Friday, 3 August 2018 at 21:49:53 UTC, Walter Bright wrote:
> I mean `std` should never be part of the fully qualified name
of, for
> instance, `core.stdcpp.exception.std.bad_exception`. It
should just
> be `core.stdcpp.exception.bad_exception` instead.

C++ recognizes that, too, which is why it has "using" declarations. D has the equivalent thing, "alias".

You can do things like:

    import std = core.stdcpp.exception;

and then refer to:

    std.bad_exception

or:

    import exception = core.stdcpp.exception;

    exception.bad_exception;

or whatever works best for one's project. Aliasing and import renaming (which are really just more aliasing) is very capable, and was designed for just these sorts of issues.

Until you want to use more than one module it falls flat on it's face:

import std = core.stdcpp.exception;
import std = core.stdcpp.vector; // as an example future use

// can't have both, error: import "std" conflicts with other import "std"
std.bad_exception
std.vector!int


Reply via email to