返回包含Rust中引用的对象

时间:2014-08-18 15:33:41

标签: rust

我有以下两种类型:

struct A {
    x: int
}

struct B<'a> {
    y: &'a A
}

我想创建一个创建A类对象的函数和一个B类对象,该对象包含对A类对象的引用,并返回B类型的对象:

fn bar<'a>() -> B<'a> {
    let y = A { x: 3 };
    B { y: &y }
}

但是我收到以下编译器错误:

main.rs:11:13: 11:14 error: `y` does not live long enough
main.rs:11     B { y: &y }
                       ^
main.rs:9:23: 12:2 note: reference must be valid for the lifetime 'a as defined on the block at 9:22...
main.rs:9 fn bar<'a>() -> B<'a> {
main.rs:10     let y = A { x: 3 };
main.rs:11     B { y: &y }
main.rs:12 }
main.rs:9:23: 12:2 note: ...but borrowed value is only valid for the block at 9:22
main.rs:9 fn bar<'a>() -> B<'a> {
main.rs:10     let y = A { x: 3 };
main.rs:11     B { y: &y }
main.rs:12 }
error: aborting due to previous error

这个错误似乎是合理的,因为我无法找到解决问题的方法。有没有办法指定y的生命周期至少应为'a,而不更改AB的定义?

1 个答案:

答案 0 :(得分:3)

无法指定y生命周期至少应为'a,因为这是不可能的:y是一个局部变量,只是不能比它在中创建的堆栈帧寿命更长。

一般情况下,如果您发现需要这样做,实际上您很可能希望B拥有A

struct B { y: A }

在这种情况下,代码变得微不足道:

fn bar() -> B {
    let y = A { x: 3 }
    B { y: y }
}

你可以从另一点看这个。这是您想要的bar()签名:

fn bar<'b>() -> B<'b> { ... }

'b是一个生命周期参数,也就是说,它可以由此函数的调用者任意选择。但是没有什么可以阻止调用者替换'static 'b

let x: B<'static> = bar();

但是,只有当bar() 始终返回B<'static>时才会出现这种情况,这似乎不是您想要的。事实上,上述签名与此完全相同:

fn bar() -> B<'static> { ... }