将带有可变引用的匹配放入函数

时间:2015-12-25 00:10:00

标签: rust

我们说我有这个代码(因为它被大大简化了,所以它是人为的):

enum Foo<'a, T> where T: 'a {
    Bar(&'a mut Vec<T>),
}

fn main() {
   let mut v = vec![1, 2];
   let foo: Foo<isize> = Foo::Bar(&mut v);
   let a = match foo {
       Foo::Bar(ref mut v) => &mut v[..],
   };
   a[1] = 10;
   println!("a = {:?}", a);
}

这很有效,每个人都很开心。但是,如果我尝试通过将match语句放在函数中来清理它,我甚至无法编译函数,更不用说让它为我工作了。我的许多尝试之一看起来像这样:

fn unpack<'a, T>(foo: Foo<'a, T>) -> &'a mut [T] {
    match foo {
        Foo::Bar(ref mut v) => &mut v[..],
    } 
}

我刚收到错误:

error: `foo.0` does not live long enough

我一直在努力改变多个生命周期并添加一个where子句(就像我必须做的那样让Enum工作),但我似乎无法让它工作。我的问题很简单,如果它有效(以及如何),或者这里唯一的选择是使用宏。

1 个答案:

答案 0 :(得分:5)

Foo::Bar(ref mut v)&mut Vec<T>借用foo,因此它不能超过foo(它只会持续到函数结束)。您实际想要做的是接受它(按值),因此您应该匹配Foo::Bar(v)

fn unpack<'a, T>(foo: Foo<'a, T>) -> &'a mut [T] {
    match foo {
        Foo::Bar(v) => &mut v[..],
    } 
}

注意:Rust会根据需要解除v,因此以下内容也可以使用:

fn unpack<'a, T>(foo: Foo<'a, T>) -> &'a mut [T] {
    match foo {
        Foo::Bar(v) => v,
    } 
}