[英]Lifetime error for method returning iterator
I am facing a weird lifetime compilation error while trying to compile following simple XOR encryption Rust code.在尝试按照简单的 XOR 加密 Rust 代码进行编译时,我遇到了一个奇怪的生命周期编译错误。
pub struct Encrypt<'a> {
key:&'a[u8],
current_index: usize,
}
impl<'a> Encrypt<'a> {
pub fn new<T: ?Sized + AsRef<[u8]>>(key: &'a T) -> Encrypt<'a> {
Encrypt { key: key.as_ref(), current_index: 0 }
}
pub fn encrypt<T, U>(&'a mut self, data: T) -> impl Iterator<Item = u8>
where T: IntoIterator<Item = U>, U: std::borrow::Borrow<u8> {
let iter = data.into_iter().map(|b| {
let val = b.borrow() ^ self.key[self.current_index];
self.current_index = (self.current_index + 1) % self.key.len();
val
});
iter
}
}
I am getting following bompilation error:我收到以下 bompilation 错误:
error[E0700]: hidden type for `impl Trait` captures lifetime that does not appear in bounds
8 | impl<'a> Encrypt<'a> {
| -- hidden type `Map<<T as IntoIterator>::IntoIter, [closure@src/lib.rs:36:41: 40:10]>` captures the lifetime `'a` as defined here
...
41 | iter
This is really strange because the method encrypt() does not return any reference, still the compiler appears to be associating the lifetime of self with it.这真的很奇怪,因为方法 encrypt() 不返回任何引用,但编译器似乎仍然将 self 的生命周期与它相关联。 Please suggest a solution for this problem.请为这个问题提出一个解决方案。 Thanks in advance!提前致谢!
This is a common problem that can arise from incorrect lifetime annotations.这是一个常见问题,可能由不正确的生命周期注释引起。 The issue is that you're binding the returned iterator's lifetime to the lifetime of self
which is 'a
.问题是您将返回的迭代器的生命周期绑定到self
的生命周期,即'a
。 But you don't care about the lifetime of self
, you only care about the lifetime of the reference you're borrowing to it, &mut self
, let's call that lifetime 's
.但是你不关心self
的生命周期,你只关心你借用它的引用的生命周期, &mut self
,我们称之为生命周期's
Now we just need to tell the compiler:现在我们只需要告诉编译器:
impl<'a> Encrypt<'a> {
pub fn encrypt<'s, T, U>(&'s mut self, data: T) -> impl Iterator<Item = u8> + 's
// ^^ ^^ ^^^^
// tie the return value's lifetime to the lifetime for which we burrow `self`
// instead of the whole lifetime of `self`.
where
T: IntoIterator<Item = U> + 's,
// ^^^^
// That'll transitively require this bound
U: std::borrow::Borrow<u8>,
{
let iter = data.into_iter().map(|b| {
let val = b.borrow() ^ self.key[self.current_index];
self.current_index = (self.current_index + 1) % self.key.len();
val
});
iter
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.