diff --git a/docs/docs/reference/other-new-features/parameter-untupling-spec.md b/docs/docs/reference/other-new-features/parameter-untupling-spec.md index 21e1aebd6a12..513538c39074 100644 --- a/docs/docs/reference/other-new-features/parameter-untupling-spec.md +++ b/docs/docs/reference/other-new-features/parameter-untupling-spec.md @@ -3,7 +3,7 @@ layout: doc-page title: "Parameter Untupling - More Details" --- -### Motivation +## Motivation Say you have a list of pairs @@ -35,31 +35,35 @@ xs.map(_ + _) Generally, a function value with `n > 1` parameters can be converted to a function with tupled arguments if the expected type is a unary function type of the form `((T_1, ..., T_n)) => U`. -### Type Checking +## Type Checking -Let a function `f` of the form `(p1, ..., pn) => e` for `n != 1`, parameters `p1, ..., pn`, and an expression `e`. +The type checking happens in two steps: -If the expected type of `f` is a fully defined function type or SAM-type that has a -single parameter of a subtype of `ProductN[T1, ..., Tn]`, where each type `Ti` fits the corresponding -parameter `pi`. Then `f` will conform to the function type `ProductN[T1, ..., Tn] => R`. +1. Check whether parameter untupling is feasible +2. Adapt the function and type check it + +### Feasibility Check + +Suppose a function `f` of the form `(p1, ..., pn) => e` (where `n > 1`), with `p1, ..., pn` as parameters and `e` as function body. + +If the expected type for checking `f` is a fully defined function type of the form `TupleN[T1, ..., Tn] => R` (or an equivalent SAM-type), where each type `Ti` fits the corresponding parameter `pi`. Then `f` is feasible for parameter untupling with the expected type `TupleN[T1, ..., Tn] => R`. A type `Ti` fits a parameter `pi` if one of the following two cases is `true`: * `pi` comes without a type, i.e. it is a simple identifier or `_`. * `pi` is of the form `x: Ui` or `_: Ui` and `Ti <: Ui`. -Auto-tupling composes with eta-expansion. That is an n-ary function generated by eta-expansion -can in turn be adapted to the expected type with auto-tupling. +Parameter untupling composes with eta-expansion. That is, an n-ary function generated by eta-expansion can in turn be adapted to the expected type with parameter untupling. -#### Term adaptation +### Term adaptation If the function ```scala -(p1: T1, ..., pn: Tn) => e +(p1, ..., pn) => e ``` -is typed as `ProductN[T1, ..., Tn] => Te`, then it will be transformed to +is feasible for parameter untupling with the expected type `TupleN[T1, ..., Tn] => Te`, then continue to type check the following adapted function ```scala (x: TupleN[T1, ..., Tn]) => @@ -69,12 +73,8 @@ is typed as `ProductN[T1, ..., Tn] => Te`, then it will be transformed to e ``` -##### Generic tuples - -If we come to support generic tuples, which provide the possibility of having tuples/functions of arities larger than 22 we would need to additionally support generic tuples of the form `T1 *: T2 *: ...`. -Translation of such a tuples would use the `apply` method on the tuple to access the elements instead of the `_N` methods of `Product`. - -### Migration +with the same expected type. +## Migration Code like this could not be written before, hence the new notation would not be ambiguous after adoption. @@ -82,6 +82,6 @@ Though it is possible that someone has written an implicit conversion form `(T1, for some `n`. This change could be detected and fixed by [`Scalafix`](https://scalacenter.github.io/scalafix/). Furthermore, such conversion would probably be doing the same translation (semantically) but in a less efficient way. -### Reference +## Reference For more information, see [Issue #897](https://github.com/lampepfl/dotty/issues/897).