提问人:FreelanceConsultant 提问时间:9/2/2023 最后编辑:cafce25FreelanceConsultant 更新时间:9/2/2023 访问量:28
如何表达接受和返回引用的闭包的生存期约束?
How to express lifetime constraints for closures which take and return references?
问:
我在 Rust playground 中勾勒出一个示例问题。
作为参考,我将在这个问题的末尾提供完整的代码。
我尝试编写以下函数。
fn get_longest_time_window(&self) -> Option<u64> {
let lambda = |lhs: &Element, rhs: &Element| -> &Element {
return
if lhs.time_window >= rhs.time_window {
lhs
}
else {
rhs
}
};
let selected = self.data.iter().reduce(lambda);
// ...
此函数在 上运行。我试图遍历这个数据结构并对其应用一个reduce闭包。self.data
此闭包接受对 中元素对的引用,并返回对其中一个元素的引用。返回的引用在迭代结束时仍然有效,因为内存中的任何数据均未被删除或以其他方式更改,从而导致重新分配,从而使引用无效。data
selected
应包含Option<&Element>
上面表明这段代码应该是有效的,但它没有编译,因为闭包谈到了 3 个引用,并且不知道它们之间的相对生存期是多少。
我猜生命周期应该都是一样的,但我不知道如何用 Rust 语法来表达。
我试图写的东西是否有效,如果是,可以做些什么来使其编译?
法典:
use std::collections::BTreeSet;
struct Element {
pub data: String, // arbitrary
pub time_window: u64,
}
struct Machine {
data: BTreeSet<Element>
}
impl Machine {
fn new() -> Machine {
let machine = Machine {
data: BTreeSet::new()
};
return machine;
}
fn get_longest_time_window(&self) -> Option<u64> {
let lambda = |lhs: &Element, rhs: &Element| -> &Element {
return
if lhs.time_window >= rhs.time_window {
lhs
}
else {
rhs
}
};
let selected = self.data.iter().reduce(lambda);
return selected.map(|x| {x.time_window});
}
}
fn main() {
let machine = Machine::new();
let max_time_window = machine.get_longest_time_window();
println!("max_time_window = {:?}", max_time_window);
}
答:
0赞
cafce25
9/2/2023
#1
在你的情况下,你实际上并不需要闭包,因为它不会捕获任何环境,一个常规函数将起作用:
fn get_longest_time_window(&self) -> Option<u64> {
fn lambda<'a>(lhs: &'a Element, rhs: &'a Element) -> &'a Element {
return if lhs.time_window >= rhs.time_window {
lhs
} else {
rhs
};
}
//…
}
一旦closure_lifetime_binder
稳定或每晚打开,您可以使用它们在闭合上指定相同的内容:
#![feature(closure_lifetime_binder)]
//…
let lambda = for<'a> |lhs: &'a Element, rhs: &'a Element| -> &'a Element { /* … */ };
评论
0赞
FreelanceConsultant
9/2/2023
谢谢,这是一个简单的解决方案,所以我就去吧
评论