Capture Clauses as Effects

https://lobste.rs/rss Hits: 23
Summary

IntroductionIn my post on Hoisting Expressions I discussed the move($expr) feature and how it works much like an inverse of the defer feature many languages have. Instead of creating expressions which run after the scope ends, move($expr) runs code before the scope is entered . The goal of this code is to make it so clone-heavy ecosystems like bevy have a much better experience using Rust. Even though I agree with the goals, I’m less sure about the proposal. I feel that explicit capture clauses provide a simpler model and are therefore preferable. But they have the downside they can feel a bit clunky to write and can break up the writing flow. And so in this post I want to explore a potential solution here by making the conversion of references to owned values a first-class language feature. Setting the stageLet’s start by using a simplified version of the motivating example shown in RFC 3968. This here is a typical task::spawn example you’ll see in a lot of async Rust programs . It clones some fields out of a struct, moves those into the closure, and passes those to another function: let a = foo.a.clone(); let b = foo.b.clone(); let c = foo.c.clone(); task::spawn(async move { bar(a, b, c).await });CopyThe problem with this code is that it is a fair bit of ceremony. Variable shadowing can sometimes create problems with naming, each clone lives on its own line, and when writing closure code you’ll often find yourself jumping back and forth to make sure you’re cloning the right variables. If we want to improve the ergonomics of cloning this is what we’re trying to improve upon. A menagerie of movesThere are different kinds of closure captures, and for any proposed language feature it’s important to cover a full range of examples. Let’s walk through a number of them so we can refer to them later as we start working through a design: Example 1: move three variablesThe variables a, b, and c all directly moved into the closure. bar(move || { baz(a, b, c); });CopyExample 2...

First seen: 2026-07-21 16:29

Last seen: 2026-07-22 14:46