rus*_*ell 1 lifetime rust borrow-checker
我无法弄清楚是什么导致了这个引用错误:
error[E0515]: cannot return value referencing local variable `s1`
--> src/regexp/mod.rs:538:9
|
528 | match s1.step() {
| --------- `s1` is borrowed here
...
538 | steps
| ^^^^^ returns a value referencing data owned by the current function
For more information about this error, try `rustc --explain E0515`.
error: could not compile `regexp` due to previous error
Run Code Online (Sandbox Code Playgroud)
我已经创建了 CharsStep 结构克隆和复制,并且在两次推送中我都尝试推送对象的克隆并进行分配以获取副本并推送它。我以为我开始理解内存模型了,但这个模型让我陷入困境。这里借的是什么?在添加到步骤向量之前,是否所有引用都已复制(多次!)?
我查看了建议的参考,它只是解释了我所知道的,即我只能返回值,而不是对本地值的引用,但由于它们是克隆的,所以我认为它们没问题。
pub trait Walker {}
// used to hold the state at each step in the search walk, and later to build the final result if successful
#[derive(Clone, Copy)]
struct CharsStep<'a> {
node: &'a CharsNode,
string: &'a str,
matched: &'a str,
}
impl<'a> Walker for CharsStep<'a> {}
impl<'a> CharsStep<'a> {
fn walk(node: &'a CharsNode, string: &'a str) -> Vec<Box<dyn Walker + 'a>> {
let mut steps = Vec::<Box<dyn Walker>>::new();
let mut step = CharsStep {
node,
string,
matched: "",
};
if node.limit_desc.0 == 0 {
steps.push(Box::new(step.clone()));
}
for i in 1..node.limit_desc.1 {
let s1 = step;
match s1.step() {
Some(s) => {
if i >= node.limit_desc.0 {
steps.push(Box::new(s.clone()));
}
step = s.clone();
}
None => {
break;
}
}
}
steps
}
fn step(&self) -> Option<CharsStep> {
let len = self.node.string.len();
if self.string[0..len] == self.node.string {
Some(CharsStep {
node: self.node,
string: &self.string[len..],
matched: &self.string[..len],
})
} else {
None
}
}
}
Run Code Online (Sandbox Code Playgroud)
我很惊讶没有关于此的警告(甚至没有 Clippy lint)。
你忘记了一个生命周期注释,这极大地改变了含义:
fn step(&self) -> Option<CharsStep> {
Run Code Online (Sandbox Code Playgroud)
这被解释为好像您写了:
fn step<'s>(&'s self) -> Option<CharsStep<'s>> {
Run Code Online (Sandbox Code Playgroud)
当您调用时step,会创建一个临时引用,因为step需要&self. 由于缺少生命周期注释,编译器可以非常正确地判断您正在借用当前函数拥有的数据。它只能查看函数签名,这就是它所说的。
由于您实际上借用的数据self本身已借用,因此您需要将生命周期更改为与此处引用的数据相同,即'a来自 impl 上下文:
fn step(&self) -> Option<CharsStep<'a>> {
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
99 次 |
| 最近记录: |