rfc:auto-capture-lambda
Differences
This shows you the differences between two versions of the page.
Both sides previous revisionPrevious revisionNext revision | Previous revision | ||
rfc:auto-capture-lambda [2021/03/22 21:56] – crell | rfc:auto-capture-lambda [2021/03/24 15:58] (current) – Deprecate page. crell | ||
---|---|---|---|
Line 1: | Line 1: | ||
- | ====== PHP RFC: Auto-capturing lambdas ====== | + | [[rfc: |
- | * Version: 0.9 | + | |
- | * Date: 2021-03-22 | + | |
- | * Author: Nuno Maduro (enunomaduro@gmail.com), | + | |
- | * Status: Draft | + | |
- | * First Published at: http:// | + | |
- | + | ||
- | ===== Introduction ===== | + | |
- | + | ||
- | Lambdas have become increasingly powerful and useful in PHP in recent versions. | + | |
- | + | ||
- | Specifically, | + | |
- | + | ||
- | ===== Proposal ===== | + | |
- | + | ||
- | ==== Background ==== | + | |
- | + | ||
- | As of PHP 8.0, the following syntax around functions has the following meaning: | + | |
- | + | ||
- | <code php> | + | |
- | + | ||
- | // A named, globally available function. | + | |
- | // No values are auto-captured from the environment. | + | |
- | // The body is a series of statements, with possibly a return statement. | + | |
- | function foo($a, $b, $c): int { | + | |
- | return $a * $b * $c; | + | |
- | } | + | |
- | + | ||
- | // An anonymous, locally available function. | + | |
- | // Values are explicitly captured lexically. | + | |
- | // The body is a series of statements, with possibly a return statement. | + | |
- | $foo = function ($a, $b) use ($c) { | + | |
- | return $a * $b * $c; | + | |
- | }; | + | |
- | + | ||
- | // An anonymous, locally available function. | + | |
- | // Values are auto-captured lexically. | + | |
- | // The body is a single-expression, | + | |
- | $foo = fn($a, $b): int => $a * $b * $c; | + | |
- | </ | + | |
- | + | ||
- | That is, a function may be named or local/ | + | |
- | + | ||
- | The [[rfc:short-functions|Short Functions]] RFC seeks to add one additional combination: | + | |
- | + | ||
- | This RFC seeks to add a different combination: | + | |
- | + | ||
- | The remaining combinations would be: | + | |
- | + | ||
- | * named function, auto-capture, | + | |
- | * named function, auto-capture, | + | |
- | * anonymous function, manual-capture, | + | |
- | + | ||
- | ==== Auto-capture | + | |
- | + | ||
- | Specifically, | + | |
- | + | ||
- | <code php> | + | |
- | // An anonymous, locally available function. | + | |
- | // Values are auto-captured lexically. | + | |
- | // The body is a series of statements, potentially ending in a return statement; | + | |
- | $c = 1; | + | |
- | $foo = fn($a, $b) { | + | |
- | $val = $a * $b; | + | |
- | return $val * $c; | + | |
- | }; | + | |
- | </ | + | |
- | + | ||
- | The syntax choice here, in combination with short-functions, | + | |
- | + | ||
- | * The '' | + | |
- | * '' | + | |
- | * The '' | + | |
- | * The '' | + | |
- | * A function with a name is declared globally at compile time. A function without a name is declared locally as a lambda at runtime. | + | |
- | + | ||
- | These rules are easily recognizable and learnable by developers. | + | |
- | + | ||
- | ==== Methods ==== | + | |
- | + | ||
- | As methods cannot be anonymous, there are no impacts on methods from this RFC. The short-functions RFC does address methods, and does so in a way that is completely consistent with the syntactic rules defined above. | + | |
- | + | ||
- | ==== What about long-lambdas? | + | |
- | + | ||
- | The existing multi-line lambda syntax remains valid, and there is no intent to deprecate it. It is likely to become less common in practice, but it still has two use cases where it will be necessary: | + | |
- | + | ||
- | * When it is desirable to capture variables explicitly, such as to avoid name collision. | + | |
- | * When it is desirable to capture a variable by reference. | + | |
- | + | ||
- | ==== Multi-line expressions ==== | + | |
- | + | ||
- | There has been related discussion of multi-line expressions, | + | |
- | + | ||
- | As a side benefit, the syntax proposed here does offer a somewhat round-about way to have a multi-line '' | + | |
- | + | ||
- | <code php> | + | |
- | $b = ...; | + | |
- | $c = ...; | + | |
- | $ret = match ($a) { | + | |
- | 1, 3, 5 => fn() { | + | |
- | $val = $a * $b; | + | |
- | return $val * $c; | + | |
- | }(), | + | |
- | 2, 4, 6 => fn() { | + | |
- | $val = $a + $b; | + | |
- | return $val + $c; | + | |
- | }(), | + | |
- | }; | + | |
- | </ | + | |
- | + | ||
- | While sub-optimal, | + | |
- | + | ||
- | ===== Backward Incompatible Changes ===== | + | |
- | + | ||
- | None. | + | |
- | + | ||
- | ===== Proposed PHP Version(s) ===== | + | |
- | + | ||
- | PHP 8.1. | + | |
- | + | ||
- | ===== Open Issues ===== | + | |
- | Make sure there are no open issues when the vote starts! | + | |
- | + | ||
- | ===== Unaffected PHP Functionality ===== | + | |
- | + | ||
- | Existing function syntax continues to work precisely as it does now. Only new combinations are possible. | + | |
- | + | ||
- | ===== Future Scope ===== | + | |
- | + | ||
- | The proposal section detailed three additional possible combinations of function functionality that are not included here. While it is not likely that they have much use, the pattern here clearly lays out what they would be were a future RFC to try and implement them. | + | |
- | + | ||
- | Specifically, | + | |
- | + | ||
- | <code php> | + | |
- | $GLOBALS[' | + | |
- | + | ||
- | fn foo($a, $b) { | + | |
- | $val = $a * $b; | + | |
- | return $val * $c; | + | |
- | } | + | |
- | + | ||
- | fn foo($a, $b) => $a * $b * $c; | + | |
- | + | ||
- | $foo = fn($a, $b) use ($c) => $a * $b * $c; | + | |
- | </ | + | |
- | + | ||
- | Those versions are //not// included in this RFC. | + | |
- | + | ||
- | ===== Proposed Voting Choices ===== | + | |
- | + | ||
- | This is a simple Yes/No vote, requiring 2/3 to pass. | + | |
- | + | ||
- | ===== Patches and Tests ===== | + | |
- | + | ||
- | Patch is in progress from Nuno. It will be included prior to the official start of discussion. | + | |
- | + | ||
- | ===== Implementation ===== | + | |
- | After the project is implemented, | + | |
- | - the version(s) it was merged into | + | |
- | - a link to the git commit(s) | + | |
- | - a link to the PHP manual entry for the feature | + | |
- | - a link to the language specification section (if any) | + | |
- | + | ||
- | ===== References ===== | + | |
- | [[rfc: | + | |
- | + | ||
- | ===== Rejected Features ===== | + | |
- | Keep this updated with features that were discussed on the mail lists. | + |
rfc/auto-capture-lambda.txt · Last modified: 2021/03/24 15:58 by crell