为什么在Rust闭包中解引用可以避免借用问题?
Rust闭包生命周期错误:为何
*x能解决E0373? 先看这段会报错的代码:
fn broken(xs: &Vec<f32>) -> Vec<f32> { xs.iter() .flat_map(|x| xs.iter().map(|y| x - y)) .collect() }
编译器会抛出以下错误:
error[E0373]: closure may outlive the current function, but it borrows
x, which is owned by the current function
问题根源
xs.iter()返回的迭代器,每个元素都是&f32类型的引用。在flat_map的闭包里,x就是这么一个&f32,而内层的map闭包捕获了这个x引用。
Rust编译器会严格检查生命周期:flat_map要求返回的迭代器(也就是内层map生成的迭代器)不能比flat_map的闭包存活更久,但内层闭包依赖的x是外层闭包的局部变量,编译器无法保证内层迭代器的生命周期不会超过x,所以直接抛出生命周期冲突的错误。
为什么*x能解决问题?
没错,*x确实触发了复制操作——因为f32实现了Copy trait,当你解引用x(也就是*x)时,会直接复制x指向的浮点数值,把一个拥有所有权的f32值传递给内层闭包,而不是原来的引用。
这样一来,内层闭包捕获的是自己拥有的数值,不再需要借用外层的x引用,自然就不存在生命周期不匹配的问题了——编译器不用担心闭包会引用一个已经失效的变量,所以错误就消失了。
修复后的正常代码:
fn working(xs: &Vec<f32>) -> Vec<f32> { xs.iter() .flat_map(|x| xs.iter().map(|y| *x - y)) .collect() }
内容的提问来源于stack exchange,提问作者MrBulldops
相关产品推荐
相关产品推荐

