dart-lang / dart-lang/language

Static type metadata guided shorthands and features

Open
#3,905 4 comments 0 reactions 0 assignees View on GitHub
feature
Dominant language
TeX
Stars
2.9k
Forks
239
Avg merge
2d 18h
Merged PRs (30d)
14

Description

This is more of a meta-issue around the use of static information, some that is not directly part of a type, used to infer more than just types.

There are multiple features that try to rely on a static type, sometimes the context type, to allow shorthands or other features, and more features that probably ould do so.
* Enum-value shorthands, `.value`: #1183
* And the related parameter default scopes: #3834
* Shorter function literal, `=> expr`: #343
* Passing positional arguments by name, `makePoint(y: 42, x: 37)` where `x` and `y` are positional parameters. (Probably proposed somewhere).

These all rely on the static type of something, and sometimes on metadata related to that static type.
* The pass-positional-arguments-by-name depends on the static type of the function being called having names for positional parameters. A function type doesn't have to have names for positional parameters, and such names are not really part of the type, they're more like *metadata* associated with the function type.
* The shorter function literal and enum-value shorthands depend only on the static context type, but an extension of the shorter function literal *could* inherit names from that function type, so that calling a function with type `void Function(int Function(int a, int b) compare)` with a shorthand function `=> a - b` could default to using the positional parameter names of the context function type.
* The parmeter default scope associates a namespace with a parameter, which is a again meta-data for the function type. A function type can have such an extra namespace as part of its parameter, but it doesn't affect subtyping, and you can cast to and from it.

Those are all *potentially* useful features, but are not really viable in Dart without formally defining the flow of such metadata through type inference and type operations (**UP** or similar).

If this is something we *want* to do, we'll have to do that work on propagating the metadata (parameter names, parameter default scopes here, possibly other things too in the future).
If we do that work for one of these features, it may *enable* some of the other features.

We've generally shied away from giving semantics to positional parameter names outside of their scope, because doing so makes it a breaking change to rename a parameter, which it currently isn't. We'd have to accept that change if we want to use the names, or allow a function to *opt in* to its names being public - but if we expect most/all positional parameters to be public in the future, it might be better to just opt out legacy code, and have people do their final renaming before upgrading to the language version which changes it.

So, at a higher level, is this kind of "static metadata" based programming shorthands or aides something we want at all?
And if so, how far are we willing to go?

(One can see `dynamic` and `void` as similar "metadata" on a type that is really `Object?`. We're treating them as separate types, which works because the information follows the type, and we've had to define things like **MORE_TOP** to account for the static difference - that is, we've modified our type operations to preserve and combine this particular kind of metadata. So there is precedence.)

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.