首页 > 解决方案 > 如何使用 Pin 而不是 Arc 来传递 Vec通过引用异步块?

问题描述

我想Vec<u8>使用以下命令多次执行操作Arc

use futures::{
    executor::{block_on, ThreadPool},
    task::SpawnExt,
}; // 0.3.4
use std::{pin::*, sync::Arc};

fn foo(b: Arc<Vec<u8>>) {
    println!("{:?}", b);
}

#[test]
fn pin_test() {
    let v = Arc::new(vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10]);
    let mut pool = ThreadPool::new().unwrap();
    for _ in 0..10 {
        let v1 = v.clone();
        let handle = pool
            .spawn_with_handle(async {
                foo(v1);
            })
            .unwrap();
        block_on(handle);
    }
}

Pin我原Vec<u8>以为能够

use futures::{
    executor::{block_on, ThreadPool},
    task::SpawnExt,
}; // 0.3.4
use std::{pin::*, sync::Arc};

fn foo(b: &[u8]) {
    println!("{:?}", b);
}

#[test]
fn pin_test() {
    let v = Pin::new(vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10]);
    let mut pool = ThreadPool::new().unwrap();
    for _ in 0..10 {
        let v1 = v.clone();
        let handle = pool
            .spawn_with_handle(async {
                foo(&*v1);
            })
            .unwrap();
        block_on(handle);
    }
}

这给出了错误:

error[E0597]: `v1` does not live long enough
  --> src/lib.rs:19:23
   |
18 |                .spawn_with_handle(async {
   |   ________________________________-_____-
   |  |________________________________|
   | ||
19 | ||                 foo(&*v1);
   | ||                       ^^ borrowed value does not live long enough
20 | ||             })
   | ||             -
   | ||_____________|
   | |______________value captured here by generator
   |                argument requires that `v1` is borrowed for `'static`
...
23 |        }
   |        - `v1` dropped here while still borrowed

我知道Pin应该将Vec数据固定到特定点,以便所有调用都可以引用相同的数据。什么是正确的使用方法,Pin以便我可以传递参考foo()

我正在使用 Rust 1.39。

标签: rustasync-await

解决方案


您缺少一个move.

改变

let handle = pool
    .spawn_with_handle(async {
        foo(&*v1);
    })
    .unwrap();

let handle = pool
    .spawn_with_handle(async move {
        //                   ^^^^
        foo(&*v1);
    })
    .unwrap();

推荐阅读