rust 如何将泛型类型化参数移动到异步移动块?

xjreopfe  于 2023-06-30  发布在  其他
关注(0)|答案(1)|浏览(78)

我正在尝试用Rust写一些东西(我喜欢它,但还没有太多经验),发现了一个我不知道如何解决的障碍。
我的意图是生成一个异步任务,将初始状态作为参数传递。异步任务将获取该值(它可以保留该值的所有权)并进一步使用它。问题是初始值必须是泛型。我得到一个错误,抱怨StateT的生存期,我不能让编译器知道我想把它移动/复制到异步块。

async fn start<StateT>(initial_value: StateT) -> impl futures::Future
where
    StateT: Send,
{
    tokio::spawn(async move {
        process(initial_value);
    })
}

我试着做StateT: Copy + Send + Sync等,但它不喜欢它。只有'static可以工作,但我想这是不正确的(我传递的不是一个常量,而是一些任意的结构)。
错误消息为:

error[E0310]: the parameter type `StateT` may not live long enough
 --> src/workflow2.rs:7:5
  |
7 | /     tokio::spawn(async move {
8 | |         process(initial_value);
9 | |     })
  | |______^ ...so that the type `StateT` will meet its required lifetime bounds
  |
help: consider adding an explicit lifetime bound...
  |
5 |     StateT: Send + 'static,
  |                  +++++++++

如果我尝试传递一个i32String而不是泛型,它工作得很好。所以我想我缺少了一些绑定到StateT的trait,它提供了所缺少的内容。

kxkpmulp

kxkpmulp1#

只有'static可以工作,但我想这是不正确的(我传递的不是一个常量,而是一些任意的结构)。
这是常见的Rust生命周期误解#2:T: 'static并不意味着T存在于整个程序中,更不意味着T是一个常数。这只意味着T是一个完全自包含的类型,它不借用任何其他数据。所以StateT: 'static是正确的做法:

async fn start<StateT>(initial_value: StateT) -> impl futures::Future
where
    StateT: Send + 'static,
{
    tokio::spawn(async move {
        process(initial_value);
    })
}

相关问题