[Accepted] SE-0373: Lift all limitations on variables in result builders

Hello, all.

The review of SE-0373: Lift all limitations on variables in result builders ran from September 30th to October 10th. The Language Workgroup kept the review open for an extra week or so to discuss some late-breaking feedback.

Feedback was generally positive, but there were a few questions about the proposal, particularly centered around the ability to initialize an uninitialized variable and how this should work under result builders.

Many result builder DSLs wish to discourage imperative-style code within the DSL, often at least in part because it is problematic for the code to have side effects. (For example, SwiftUI view bodies can be re-evaluated unpredictably, and so any side effects will be re-executed, which is usually very bad. Along the same lines, it's important for bodies to not trigger data changes, since they can cause the body to be re-evaluated, thus re-triggering the data changes, ad infinitum.) When all the code in the DSL feels "declarative", DSL bodies feel different, and programmers are subtly encouraged to follow the rules in them. Assignment statements undermine this and encourage more imperative styles of thinking, even when they're semantically just initializing local variables after their declaration. As a result, it is important that result builders be able to disallow initializing assignments.

Fortunately, that is still possible under this proposal, and in fact it will typically just work out of the box for declarative-style DSLs. SE-0373 allows initializing assignments, but it treats them the same way that result builders already treat non-initializing assignments. The result builder transformation processes assignment statements by trying to build them into the result just like an expression of type Void. This will succeed only if the result builder allows Void expression results, which declarative-style result builders generally do not, since Void expressions are overwhelmingly likely to be side-effectful computations. As a result, declarative result builders like SwiftUI's ViewBuilder will automatically disallow initializing assignments the same way they already disallow non-initializing assignments. This is the desired behavior.

SE-0373 is therefore accepted. Thank you to everyone who participated in this review.

John McCall
Review Manager