www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - masking of module-level functions with local imports

reply Steven Schveighoffer <schveiguy yahoo.com> writes:
Consider these two imports:

a.d:
module a;
void foo(int) {}

b.d:
module b;
void foo(string) {}

Now, we import them and use them:

main.d:
import a;
import b;

void main()
{
    foo(1);
    foo("hi");
}

Works great. Now let's use a local import instead:

main.d:
import a;

void main()
{
    import b;
    foo(1);
    foo("hi");
}

oops, doesn't work. Because b masks all other overloads for foo.

I have to say, this doesn't seem right. What I want when I import inside 
a local scope is to treat all code in that scope as if I *had* imported 
that module at module level.

I realize changing this would mean that existing code would break. But 
what this does, effectively, is destroy any possibility to overload 
functions across modules reliably.

See this regression: https://issues.dlang.org/show_bug.cgi?id=15179

How can we fix this? 'to' really *is* a UFCS function, it shouldn't be a 
member. Do we just say "sorry, please make all your imports local"?

Another *horrendous* issue I have seen:

a.d:
module a;
void foo(int) {}

main.d:

void foo(string) {}
void main()
{
    import main; // yes, you have to import main inside main
    import a;
    foo("hi");
}

Can we fix this?

-Steve
Oct 08 2015
next sibling parent Jesse Phillips <Jesse.K.Phillips+D gmail.com> writes:
On Friday, 9 October 2015 at 03:52:10 UTC, Steven Schveighoffer 
wrote:
 I have to say, this doesn't seem right. What I want when I 
 import inside a local scope is to treat all code in that scope 
 as if I *had* imported that module at module level.

 I realize changing this would mean that existing code would 
 break. But what this does, effectively, is destroy any 
 possibility to overload functions across modules reliably.
Agreed. I filed the report incorrectly against DMD as I expected local imports to follow the same overload resolution with the outer import counter parts. Note that had Druntime's new 'to' function accepted strings it would have hijacked the call (no compiler error).
Oct 09 2015
prev sibling parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 10/8/15 11:52 PM, Steven Schveighoffer wrote:

 Another *horrendous* issue I have seen:

 a.d:
 module a;
 void foo(int) {}

 main.d:

 void foo(string) {}
 void main()
 {
     import main; // yes, you have to import main inside main
     import a;
     foo("hi");
 }

 Can we fix this?
Nobody else finds this to be an issue? Should we just close bugs like 15179 with "sorry, please import everything you need local or global, too bad the phobos/druntime changes broke your code"? -Steve
Oct 15 2015
next sibling parent Meta <jared771 gmail.com> writes:
On Thursday, 15 October 2015 at 14:13:34 UTC, Steven 
Schveighoffer wrote:
 Nobody else finds this to be an issue? Should we just close 
 bugs like 15179 with "sorry, please import everything you need 
 local or global, too bad the phobos/druntime changes broke your 
 code"?

 -Steve
I agree it's an issue, but there are so many bugs in the module system and Walter seems to be against fixing any of them. What else can be done in this situation?
Oct 15 2015
prev sibling parent reply Jonathan M Davis <jmdavisProg gmx.com> writes:
On Thursday, 15 October 2015 at 14:13:34 UTC, Steven 
Schveighoffer wrote:
 Nobody else finds this to be an issue? Should we just close 
 bugs like 15179 with "sorry, please import everything you need 
 local or global, too bad the phobos/druntime changes broke your 
 code"?
It's an issue, but I confess that I kind of gave up on local imports working correctly when they refused to make UFCS work with local imports (though IIRC, that was specifically Kenji and not Walter - I don't know where Walter sits on it). I really don't think that local imports should be any different from imports at the module level except for the fact that they don't affect stuff at outer scopes, but I gather that the implementation doesn't jive well with that, and that's led to refusals to make imports work the same at all levels when various issues like this have come up. That being said, D's module system does tend to have issues when adding symbols to druntime, Phobos, or any library that someone else might use. So, on some level, we're always going to have this problem, but we can and should do better with that then we do (e.g. making it so that private symbols never conflict with anything when the module that they're in is imported). - Jonathan M Davis
Oct 15 2015
parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 10/15/15 10:31 AM, Jonathan M Davis wrote:
 On Thursday, 15 October 2015 at 14:13:34 UTC, Steven Schveighoffer wrote:
 Nobody else finds this to be an issue? Should we just close bugs like
 15179 with "sorry, please import everything you need local or global,
 too bad the phobos/druntime changes broke your code"?
It's an issue, but I confess that I kind of gave up on local imports working correctly when they refused to make UFCS work with local imports
Huh? UFCS works with local imports. void main() { import std.conv: to; import std.stdio: writeln; 1.to!string.writeln; // works }
 (though IIRC, that was specifically Kenji and not Walter - I don't know
 where Walter sits on it). I really don't think that local imports should
 be any different from imports at the module level except for the fact
 that they don't affect stuff at outer scopes, but I gather that the
 implementation doesn't jive well with that, and that's led to refusals
 to make imports work the same at all levels when various issues like
 this have come up.
Do you have links to these refusals? I didn't know this was considered and rejected.
 That being said, D's module system does tend to have issues when adding
 symbols to druntime, Phobos, or any library that someone else might use.
 So, on some level, we're always going to have this problem, but we can
 and should do better with that then we do (e.g. making it so that
 private symbols never conflict with anything when the module that
 they're in is imported).
Any time we duplicate any symbol name between 2 modules, we can cause regressions. If we don't fix this, either we never name any symbol the same thing in 2 modules, or we simply close as invalid any bug that depends on using local vs. global imports. I'm OK with the latter, the former is likely impossible. But some official position should be taken here. And the requirement to import the module you are currently in, just smells. A lot. -Steve
Oct 15 2015
parent Jonathan M Davis <jmdavisProg gmx.com> writes:
On Thursday, 15 October 2015 at 15:07:37 UTC, Steven 
Schveighoffer wrote:
 On 10/15/15 10:31 AM, Jonathan M Davis wrote:
 On Thursday, 15 October 2015 at 14:13:34 UTC, Steven 
 Schveighoffer wrote:
 Nobody else finds this to be an issue? Should we just close 
 bugs like
 15179 with "sorry, please import everything you need local or 
 global,
 too bad the phobos/druntime changes broke your code"?
It's an issue, but I confess that I kind of gave up on local imports working correctly when they refused to make UFCS work with local imports
Huh? UFCS works with local imports. void main() { import std.conv: to; import std.stdio: writeln; 1.to!string.writeln; // works }
Then that changed at some point, or my memory sucks right now. I recall there being a bug on it that was closed by Kenji, because supporting it caused other problems. So, if that works now, then there's hope.
 (though IIRC, that was specifically Kenji and not Walter - I 
 don't know
 where Walter sits on it). I really don't think that local 
 imports should
 be any different from imports at the module level except for 
 the fact
 that they don't affect stuff at outer scopes, but I gather 
 that the
 implementation doesn't jive well with that, and that's led to 
 refusals
 to make imports work the same at all levels when various 
 issues like
 this have come up.
Do you have links to these refusals? I didn't know this was considered and rejected.
This specific issue may not have been, but it seems like every time I read a bug related to issues with local imports, local imports end up being treated as special for whatever combination of reasons. But given the fact that I was wrong about the UFCS issue, either my memory on this is suspect at the moment, or they changed how they were treating issues like this. Regardless, this issue is just plain ugly, and ideally, we really would get the situation fixed.
 And the requirement to import the module you are currently in, 
 just smells. A lot.
That stinks to high heaven. - Jonathan M Davis
Oct 15 2015