Join GitHub today
GitHub is home to over 31 million developers working together to host and review code, manage projects, and build software together.
Sign upMultiple globs are basically unusable #553
Comments
This comment has been minimized.
This comment has been minimized.
|
The motivation for the change is avoiding shadowing. That was discussed in RFC 116. Globs are still very useful, just as long as there are no overlapping public names, in which case the user should import individual items and not use globs (since there is no explicit way to specify which name to use). So, how can we make this better? I see a few solutions:
Any more ideas? |
nrc
referenced this issue
Jan 4, 2015
Closed
`use core::prelude::*` conflicts with `use collections::slice::SliceExt` #20513
This comment has been minimized.
This comment has been minimized.
|
How about only complaining if you try to use a name that shows up in 2 glob On Sun, Jan 4, 2015, 12:17 PM Nick Cameron notifications@github.com wrote:
|
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
|
Another way we could admit more programs is only to error if two globs import the same name and that name is actually used. I.e., double import is OK, but using a double import is an error. That would certainly be more flexible. It would introduce some kind of weird errors when you start using a double-imported name though, especially around traits, which are often not explicitly named. |
This comment has been minimized.
This comment has been minimized.
|
On a second reading, I think @sfackler is suggesting exactly what I was above, not making a distinction between single and glob imports. I guess that is a hazard of |
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
|
I like @nikomatsakis WIP proposal, which basically merges all glob imported items, and only produces conflicting import error message for the concrete item (like @sfackler and @nrc propose). It also allows glob imports to be shadowed by other items including specific imports, which makes them more resilient against upstream changes, and allows to resolve conflicts by writing out a concrete import. use a::*; // a exports foo::x, foo::y, foo::z, foo::v
use b::*; // b exports foo::x, bar::y, bar::z, bar::v
let _ = x; // Valid, because both globs import the same logical item
struct z;// Valid, and doesn't conflict with glob imported items because it shadows them
let _ = z;
let _ = y; // error: ambiguous name, can only be reached through more than one glob import
// help: use a::y; or use b::y; to resolve.
use a::v;
let _ = v; // Valid, picks a specific import by shadowing the glob ones with the concrete import above.In other words, glob imports would never conflict with any other item directly, and only act as a fallback for the case that no concrete item or import in a module match. |
This comment has been minimized.
This comment has been minimized.
paulp
commented
Jun 18, 2015
|
Please don't ignore previous work. In scala you can see exactly how each idea being proposed here has played out over roughly a decade and billions of lines of code. Scala Issue Database I am not suggesting you imitate scala. But given the existence of this huge body of data, it would be professional negligence to design the same feature in a vacuum as if this has never come up before. If those sound like strong words, it's because the same is true of numerous other rust language features, and each looks to have been designed without analyzing what has and hasn't worked in scala. It is said that rust is "stable" now, for some definition thereof. Rust's history reveals an awful lot of figuring out what doesn't work by shipping and seeing what happens. Probably sometimes it has to be like that, but not generally. I don't think it's a luxury you have anymore. |
This comment has been minimized.
This comment has been minimized.
|
I don't have any particular opinions yet about this issue, and I do agree that we should pay close attention to previous work. Thanks for the links, @paulp .
This is the idea with feature gates: we can actually add new stuff, and give it a try, and it won't affect stable users. So we do kind of have this option, in certain cases. New glob behavior might not be one of them, but in the general case, this option is very much still open. |
This comment has been minimized.
This comment has been minimized.
paulp
commented
Jun 18, 2015
|
As I think I've seen acknowledged elsewhere, N gated features effectively partition the language into 2^N dialects. In a narrow sense you can preserve stability of individual dialects by raising the value of N, but there is previous work here as well, and from it we can see it's easy to win the battle and lose the war. |
Kimundi
referenced this issue
Sep 21, 2015
Open
Improve the remaining rough corners of the module system #1289
This comment has been minimized.
This comment has been minimized.
bruno-medeiros
commented
Nov 3, 2016
use a::*; // a exports foo::x, foo::y, foo::z, foo::v
use b::*; // b exports foo::x, bar::y, bar::z, bar::v
let _ = x; // Valid, because both globs import the same logical item
struct z;// Valid, and doesn't conflict with glob imported items because it shadows them
let _ = z;
let _ = y; // error: ambiguous name, can only be reached through more than one glob import
// help: use a::y; or use b::y; to resolve.+1 for the changes above. Also note that this problem is not limited to glob imports, but can happen even with just single imports - (see https://internals.rust-lang.org/t/annoying-limitations-with-use-of-same-symbols/4310?u=bruno_medeiros for a simplified version of a case I've hit in real code) use a::v;
let _ = v; // Valid, picks a specific import by shadowing the glob ones with the concrete import above.Hum.... I'm not so sure about this one. I think it might be better if glob imports were semantically the same as individually importing each specific element - making the above code still invalid. It might be confusing otherwise, or have unintended consequences. I think a |
This comment has been minimized.
This comment has been minimized.
|
Resolved by #1560, implemented and stabilized. The example compiles on stable 1.19 (and couple of previous releases). #![allow(unused)]
use a::*; // OK
use b::*; // OK
mod a { pub fn foo() {} }
mod b { pub fn foo() {} }
fn main() {}The error is reported only when the ambiguous fn main() {
foo(); //~ ERROR `foo` is ambiguous
} |
SiegeLord commentedJan 4, 2015
Copy of rust-lang/rust#20461.
A recent change broke this code:
This gives an error:
This makes globs a lot less useful than they were before. If globs are going to be only useful in isolation, why have them as a feature at all?