Rust:由于需求冲突,无法为 autoref 推断合适的生命周期

时间:2021-05-12 01:51:13

标签: rust

最少的可重现代码:

trait VecExt<T, R> {
    fn map(&self, f: impl Fn(&T) -> R) -> Vec<R>;
}

impl<T, R> VecExt<T, R> for Vec<T> {
    fn map(&self, f: impl Fn(&T) -> R) -> Vec<R> {
        self.iter().map(f).collect()
    }
}

struct A {
    a: Vec<Option<String>>
}

impl A {
    fn foo(&self) -> Vec<Option<&String>> {
        self.a.map(|o| o.as_ref())
    }
}

获取错误信息:

error[E0495]: cannot infer an appropriate lifetime for autoref due to conflicting requirements

当使用 self.a.iter().map(|o| o.as_ref()).collect() 时,它会编译。

我已经阅读了解释文档,但我仍然不知道为什么会出现这个错误以及如何解决。

1 个答案:

答案 0 :(得分:0)

map 中的 A.foo 调用被 map 函数中的代码替换时,它会编译,这表明问题在于特征定义没有限制生命周期传递给闭包的参数。

fn map(&self, f: impl Fn(&T) -> R) -> Vec<R> 的情况下,在 &T 中作为 impl Fn(&T) -> R 传递的引用的生命周期必须至少与传递给它的 &self 参数一样长。以下更改应使其编译

trait VecExt<'a, T, R> where T: 'a {
    fn map(&'a self, f: impl Fn(&'a T) -> R) -> Vec<R>;
}

impl<'a, T, R> VecExt<'a, T, R> for Vec<T> where T: 'a {
    fn map(&'a self, f: impl Fn(&'a T) -> R) -> Vec<R> {
        self.iter().map(f).collect()
    }
}