我想用访问器函数声明一个枚举,该函数返回创建值时提供的值。下面是一个说明错误的人为示例:
use std::mem;
#[derive(Debug)]
enum SomeBytes<'a> {
One([u8; 1]),
Two([u8; 2]),
}
impl SomeBytes<'a> {
pub fn get_bytes(&'a self) -> &'a[u8] {
use SomeBytes::*;
match *self {
One(byte_array) => &byte_array,
Two(byte_array) => &byte_array,
}
}
}
fn main() {
let var1 = SomeBytes::One(*b"A");
let var2 = SomeBytes::Two(*b"AB");
println!("one byte = {:?}", var1);
println!("sizeof one byte = {:?}", mem::size_of_val(&var1));
println!("two bytes = {:?}", var2);
println!("sizeof two bytes = {:?}", mem::size_of_val(&var2));
}
错误:
Compiling playground v0.0.1 (/playground)
error[E0261]: use of undeclared lifetime name `'a`
--> src/main.rs:9:16
|
9 | impl SomeBytes<'a> {
| ^^ undeclared lifetime
error[E0261]: use of undeclared lifetime name `'a`
--> src/main.rs:11:21
|
11 | pub fn get_bytes(&'a self) -> &'a[u8] {
| ^^ undeclared lifetime
error[E0261]: use of undeclared lifetime name `'a`
--> src/main.rs:11:34
|
11 | pub fn get_bytes(&'a self) -> &'a[u8] {
| ^^ undeclared lifetime
我如何编写此代码以便编译?
如果我从代码中删除了所有生存期(不需要当前的注释/答案,那么该示例如下所示:
use std::mem;
#[derive(Debug)]
enum SomeBytes {
One([u8; 1]),
Two([u8; 2]),
}
impl SomeBytes {
pub fn get_bytes(&self) -> &[u8] {
use SomeBytes::*;
match *self {
One(byte_array) => &byte_array,
Two(byte_array) => &byte_array,
}
}
}
fn main() {
let var1 = SomeBytes::One(*b"A");
let var2 = SomeBytes::Two(*b"AB");
println!("one byte = {:?}", var1);
println!("sizeof one byte = {:?}", mem::size_of_val(&var1));
println!("two bytes = {:?}", var2);
println!("sizeof two bytes = {:?}", mem::size_of_val(&var2));
}
这给了我以下错误:
Compiling playground v0.0.1 (/playground)
error[E0515]: cannot return value referencing local variable `byte_array`
--> src/main.rs:14:5
|
14 | / match *self {
15 | | One(byte_array) => &byte_array,
16 | | Two(byte_array) => &byte_array,
| | ----------- `byte_array` is borrowed here
17 | | }
| |_____^ returns a value referencing data owned by the current function
error[E0515]: cannot return value referencing local variable `byte_array`
--> src/main.rs:14:5
|
14 | / match *self {
15 | | One(byte_array) => &byte_array,
| | ----------- `byte_array` is borrowed here
16 | | Two(byte_array) => &byte_array,
17 | | }
| |_____^ returns a value referencing data owned by the current function
为了解决上述错误,我必须增加生命周期,但这不是解决方案。我试图告诉编译器我不想返回当前函数所拥有的东西……有人可以解释适当的解决方法吗?
答案 0 :(得分:3)
Stargateur给出了没有解释的代码;让我们看看我是否可以填补空白。
您的代码无法正常工作的原因是,在struct
上声明生存期将此生存期与struct 相关联。换句话说,在每种情况下,使用或返回'a
的每种方法都将采用或返回相同的'a
,而不论其放置位置和方式如何。如果您在struct
中有一个引用,而您却没有,那么这是值得的。因此,这不是必需的。
如果您想全力以赴并指定生命周期,则可以这样做:
#[derive(Debug)]
enum SomeBytes {
One([u8; 1]),
Two([u8; 2]),
}
impl SomeBytes {
pub fn get_bytes<'a>(&'a self) -> &'a [u8] {
use SomeBytes::*;
match self {
One(ref byte_array) => byte_array,
Two(ref byte_array) => byte_array,
}
}
}
生存期定义为方法的属性,而不是struct
的属性。它的附加要求是显而易见的-&self
的生命周期'a
必须保证其返回参数也要遵守。
但是,这是修脚。实际上,此生存期要求不是强制性的,可以放弃使用更简单,更自动化的版本:
pub fn get_bytes(&self) -> &[u8] {
use SomeBytes::*;
match self {
One(ref byte_array) => byte_array,
Two(ref byte_array) => byte_array,
}
}
注意:为了使示例生效,还需要在比赛右侧的&
之前删除byte_array
。由于您的方法采用&self
,因此即使您匹配自身,模式匹配的内容也将是引用自身(因为您没有对象的所有权),因此,&
将导致参考文献