DIP16: Transparently substitute module with package
Steven Schveighoffer
schveiguy at yahoo.com
Thu Apr 5 04:46:38 PDT 2012
On Wed, 04 Apr 2012 20:50:49 -0400, Michel Fortin
<michel.fortin at michelf.com> wrote:
> On 2012-04-04 19:48:32 +0000, "Steven Schveighoffer"
> <schveiguy at yahoo.com> said:
>
>> On Wed, 04 Apr 2012 14:03:07 -0400, Timon Gehr <timon.gehr at gmx.ch>
>> wrote:
>>
>>> No symbol is resolved until semantic, but I don't think hiding the
>>> module/package symbol if any clashing symbol in the module/any
>>> subpackage exists is a satisfactory solution.
>> Then we must come up with a way to hide the submodules of a virtual
>> module.
>> I tried this, which fails on the current compiler:
>> import x;
>> int x;
>> So it seems we have two choices here:
>> 1. DIP16 needs to get more complex to make package submodules not
>> accesible as individual modules.
>> 2. Start contextually interpreting identifiers at least in the case of
>> modules vs. non-modules.
>> I'd suggest option 2 allows for better backwards compatibility and
>> more flexibility.
>
> I don't think option 2 is realistic (see my other post).
I saw your other post. I see that a major issue with the way DIP16
intends to shortcut fully qualified names is demonstrated by this simple
example:
a/b/c.d:
module a.b.c;
void foo() {}
struct c
{
static void foo() {}
}
main.d:
import a.b.c;
void main()
{
a.b.c.foo(); // cannot determine what this is. Is it the global
function, or a shortcut FQN to a.b.c.c.foo?
}
This should be counter-case enough to disqualify that idea -- it will
break existing code without ever adding any package.d files. Thanks for
explaining.
>
> I don't think option 1 is an improvement over what we have. I mean, if
> you're going to hide the submodules, what is the benefit compared to
> just using a different package name for the implementation modules?
The advantage is you can split your logical module into submodules for
maintenance purposes.
> You can already refactor std.algorithm this way with no change in the
> compiler:
>
> module std.algorithm;
>
> public import std.algorithm_impl.sort;
> public import std.algorithm_impl.map;
> public import std.algorithm_impl.blah_blah_blah;
> …
>
> If we add a language feature, it should be an noticeable improvement
> over this situation.
I agree, option 1 is not very convincing.
> I think we need a third option.
>
> Here's an idea: we could allow modules having a single symbol with the
> same name as the module to behave as if they were the symbol itself,
> just like templates behaves. For instance:
>
> module std.algorithm.sort;
>
> void sort(int[] t);
>
> Now you can import std.algorithm.sort and then use the
> std.algorithm.sort fully qualified name as if it was a function, even
> though it's the module name (std.algorithm.sort.sort would be the
> function's name).
>
> Or maybe we could just allow "alias sort this" at module level? Or is it
> allowed already?
I don't like this proposal, simply because this means one function/symbol
per submodule. It should be more flexible than that. But I like the line
of thinking.
Let's re-examine the issue. We need to allow splitting of a module X.d
into pieces for maintenance (or possibly accessibility -- disallowing
friends). But we don't want to break code which currently uses FQN to
access X's symbols.
I think the following might work:
algorithm.d:
import this = std.algorithm_impl.sort;
Which then imports std.algorithm_impl.sort, and effectively aliases all
its symbols into algorithm.d. If std.algorithm_impl.sort defines a
function called sort, then it's also aliased to std.algorithm.sort. In
essence, sort has *two* FQN, but there are no FQN that refer to more than
one symbol.
I purposely left out the package.d idea because it's orthogonal to this.
-Steve
More information about the Digitalmars-d
mailing list