-
Notifications
You must be signed in to change notification settings - Fork 213
Dart variadic Set constructor #53
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
I really hate giving the core libraries special magic powers. Every time we do that, we end up frustrating users who have similar legitimate use cases. (See: patch files and config-specific imports, overloaded return types on arithmetic operators, the hand-picked set of APIs allowed in const expressions, sealing the primitive types like num, etc.) I don't think we should do this unless we also add user-defined varargs. If we do that, then this seems reasonable to me. |
I agree with Bob. If we will never add varargs, then we should just use We do already give core library special magic powers when it comes to constants and to literals. The only classes that have literals (aka. language syntax support) are List, Map, Symbol, Type, int, double, bool, String, and Null (and, arguably, function types). Those are core types. Any other class needs to go through a constructor to create an instance. Anything non-trivial that you can do in a Adding a constant set literal puts us squarely in that category of things, so it would not be unprecedented to add magic. |
This is the only compelling argument I've heard for varargs. It's pretty compelling though. |
The spread operator is actually a problem with the If we do get varargs/rest arguments, we should probably be able to spread into, at least, those parameters, so we would allow |
This is true, but I believe we should aim to reduce the amount of magic over time, not double down on it. My experience has been that anything so useful that we language/core lib folks give ourselves the magic power to use is also useful for other people too.
Yes, I don't think it makes sense to support rest parameters without a spread operator. Otherwise, users will find themselves in this situation: // Code you don't control.
expectsRest(List ...things) { /* code */ }
// Also code you don't control.
List returnsList() { /* code */ }
main() {
var stuff = returnsList();
expectsRest(/* want to pass stuff here... */); // Aww dang. :(
} Every language I know that has rest parameters or varargs has a mechanism for passing a collection of objects as a set of rest parameters. The only exception is Swift, and it's an open issue there. The rest params proposal I wrote includes a spread syntax for arguments for this reason. |
I wouldn't view this as adding magic. I'd view this like typedef FutureOr<T> = Future<T> | T; Similarly we will eventually have varargs, at which point we reimplement Set(...) as varargs. Magic is something we can't explain. We can explain both of these, just not in terms of something that exists yet. |
If we decide to do varargs. But I'm really hesitant to effectively commit ourselves to needing a feature without committing the time to do the feature. FutureOr is a good example. It's almost two years old now and we still don't have real union types in the language or immediate plans to add them.
True, but we can't implement them in terms of something that doesn't exist yet. If we add a variadic constructor for Set, then:
Etc. At that point, we may as well just do rest params. |
Two years is nothing on the grand scheme of things. You have to think of language and API development on the time scale of decades. |
We have decided to not use this idea.
Proposal for #36
I'll write the design in-line here. It's short enough that a separate document shouldn't be needed.
Proposal
The current factory
Set
constructor declared indart:core
has no parameters.When called as
Set()
it creates an empty linked hash-set.It cannot be called as
const
since it is not a const constructor.The specification will add the following clause for non-const constructor invocations:
For const constructor invocations, we add:
Future Compatibility
This design assumes no feature other than the ones already in the language.
If Dart received "varargs", then we could define
Set
as a variadic constructor and handle the non-constant case in normal code. The constant case still needs special handling since that constructor cannot be constant. We will likely define the constructor asexternal const factory Set([... elements]);
which means that the platform can cheat without violating any syntactic rules.The text was updated successfully, but these errors were encountered: