方便的方法将带有Cow字段的结构体转换为拥有所有权的结构体

6

我有一个定义如下的结构体

struct Foo<'a> {
    field1: &'a str,
    field2: &'a str,
    field3: &'a u8,
    // ...
}

我使用mmap映射文件来返回解析结果。对于一些成功的解析,我希望将结果存储以便后续处理,但由于各种原因,这些处理将在内存被释放之后进行。我可以采取以下方法:

struct OwnedFoo {
    field1: String,
    field2: String,
    field3: Vec<u8>,
    // ...
}

我想把所有我感兴趣的Foo手动转换成OwnedFoos。但是我在想是否可以这样做:

struct Foo<'a> {
    field1: Cow<'a, str>,
    field2: Cow<'a, str>,
    field3: Cow<'a, u8>,
    ...
}

我想知道是否有一种方法可以自动拥有所有的,并擦除生命周期参数。我在库文档中没有找到任何相关的内容。

类似于:

let a = Foo { ... };
let a_owned = a.into_owned();
// do stuff with a_owned that I can't do with a

在你的示例中,“a_owned”的类型是什么?你也希望它是“Foo”吗? - Lukas Kalbertodt
我希望它是一个擦除了生命周期参数的 Foo,但更关心的是使用的人体工程学。也就是说,不必定义新类型。 - dnaq
1个回答

10

构建模块:

  • Cow::into_owned 将返回拥有的版本。
  • 'static 是程序的生命周期

因此,我们可以编写一个实用函数:

use std::borrow::Cow;

fn into_owned<'a, B>(c: Cow<'a, B>) -> Cow<'static, B>
    where B: 'a + ToOwned + ?Sized
{
    Cow::Owned(c.into_owned())
}

您可以通过对所有字段应用变换,将Foo<'a> 拓展为 Foo<'static>

你知道是否有办法为Foo定义IntoOwned,以便foo.into_owned()会返回一个Foo<'static>吗? - dnaq
1
@dnaq:当然,你只需要两个实现:impl<'a> Borrow<Foo<'a>> for Foo<'static>,然后是 impl<'a> ToOwned for Foo<'a> { type Owned = Foo<'static>; } - Matthieu M.
1
似乎我无法为Borrow添加那个实现,因为存在冲突的特质边界。我猜测问题在于生成impl<'a> Borrow<Foo<'a>> for Foo<'static>时'a == 'static的实例化。 - dnaq

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接