繁体   English   中英

如何定义从 class 生成的 tokio 任务的生命周期?

[英]How do I define the lifetime for a tokio task spawned from a class?

我正在尝试编写一个通用的set_interval function 助手:

pub fn set_interval<F, Fut>(mut f: F, dur: Duration)
where
    F: Send + 'static + FnMut() -> Fut,
    Fut: Future<Output = ()> + Send + 'static,
{
    let mut interval = tokio::time::interval(dur);

    tokio::spawn(async move {
        // first tick is at 0ms
        interval.tick().await;
        loop {
            interval.tick().await;
            tokio::spawn(f());
        }
    });
}

这工作正常,直到从 class 内部调用它:

fn main() {}

struct Foo {}

impl Foo {
    fn bar(&self) {
        set_interval(|| self.task(), Duration::from_millis(1000));
    }
    
    async fn task(&self) {
        
    }
}

self不是'static ,我们不能因为tokio::task将生命周期参数限制为小于'static的东西。

是否可以修改set_interval实现以便在这种情况下工作?


链接到游乐场


PS试图

let instance = self.clone();
set_interval(move || instance.task(), Duration::from_millis(1000));

但我也收到一个错误:错误:捕获的变量无法逃脱FnMut闭包体

是否可以修改 set_interval 实现以便在这种情况下工作?

并不真地。 虽然spawn -ing f()也确实没有帮助,因为它排除了一个简单的“回调拥有对象”解决方案(因为您需要回调和未来来拥有 object,或者只是未来)。

我认为这留下了两个解决方案:

  1. 将所有内容转换为共享可变性Arc ,回调拥有一个Arc ,然后在每次滴答时克隆它并将克隆移动到未来( task方法)。
  2. 让未来( task )从某个外部源获取 object 而不是被调用,这样中间回调不需要做任何事情。 或者回调可以进行获取并将其移动到未来,相同的差异。

顺便说一句,在这一点上直接创建未来是有意义的,但允许克隆它。 因此,不是采用回调set_interval而是采用可克隆的未来,它会spawn()其存储的未来的克隆,而不是重新创建它们。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM