Given this code:
use std::thread;
#[derive(Debug)]
struct ImportantStruct {}
fn main() {
let mut data = vec![42, 42, 42, 42];
let s = ImportantStruct{};
thread::scope(|scope| {
for (index, foo) in data.drain(..).enumerate() {
scope.spawn(|| println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
}
});
}
The rust compiler fails with the following error message:
error[E0373]: closure may outlive the current function, but it borrows `foo`, which is owned by the current function
--> src/main.rs:12:25
|
10 | thread::scope(|scope| {
| ----- has type `&'1 Scope<'1, '_>`
11 | for (index, foo) in data.drain(..).enumerate() {
12 | scope.spawn(|| println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
| ^^ may outlive borrowed value `foo` --- `foo` is borrowed here
|
note: function requires argument type to outlive `'1`
--> src/main.rs:12:13
|
12 | scope.spawn(|| println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
help: to force the closure to take ownership of `foo` (and any other referenced variables), use the `move` keyword
|
12 | scope.spawn(move || println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
| ++++
error[E0373]: closure may outlive the current function, but it borrows `index`, which is owned by the current function
--> src/main.rs:12:25
|
10 | thread::scope(|scope| {
| ----- has type `&'1 Scope<'1, '_>`
11 | for (index, foo) in data.drain(..).enumerate() {
12 | scope.spawn(|| println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
| ^^ may outlive borrowed value `index` ----- `index` is borrowed here
|
note: function requires argument type to outlive `'1`
--> src/main.rs:12:13
|
12 | scope.spawn(|| println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
help: to force the closure to take ownership of `index` (and any other referenced variables), use the `move` keyword
|
12 | scope.spawn(move || println!("thread {} doing {} while having a borrow on {:?}", index, foo, &s));
| ++++
For more information about this error, try `rustc --explain E0373`.
error: could not compile `playground` due to 2 previous errors
For some reason it is unable to copy the (copyable) index into the the scoped thread's scope, and I do not understand why.
Is something wrong with my code, or is this a rustc (rustc 1.63.0 (4b91a6ea7 2022-08-08)) bug? Should '1 in the error message have been replaced by something?