rust - 是否可以在不分配新 Vec 的情况下将函数映射到 Vec 上?

标签 rust

我有以下内容:

enum SomeType {
    VariantA(String),
    VariantB(String, i32),
}

fn transform(x: SomeType) -> SomeType {
    // very complicated transformation, reusing parts of x in order to produce result:
    match x {
        SomeType::VariantA(s) => SomeType::VariantB(s, 0),
        SomeType::VariantB(s, i) => SomeType::VariantB(s, 2 * i),
    }
}

fn main() {
    let mut data = vec![
        SomeType::VariantA("hello".to_string()),
        SomeType::VariantA("bye".to_string()),
        SomeType::VariantB("asdf".to_string(), 34),
    ];
}

我现在想对 data 的每个元素调用 transform 并将结果值存储回 data。我可以做类似 data.into_iter().map(transform).collect() 的操作,但这会分配一个新的 Vec。有没有办法就地执行此操作,重新使用分配给 data 的内存? Rust 中曾经有 Vec::map_in_place,但不久前已被删除。

作为变通方法,我向 SomeType 添加了一个 Dummy 变体,然后执行以下操作:

for x in &mut data {
    let original = ::std::mem::replace(x, SomeType::Dummy);
    *x = transform(original);
}

这感觉不对,我必须在代码中的其他任何地方处理 SomeType::Dummy,尽管它永远不应该在此循环之外可见。有更好的方法吗?

最佳答案

您的第一个问题不是map,而是transform

transform 拥有其参数的所有权,而 Vec 拥有其参数的所有权。任何一个都必须放弃,在 Vec 上戳一个洞是个坏主意:如果 transform 发生 panic 怎么办?


因此,最好的解决方法是将 transform 的签名更改为:

fn transform(x: &mut SomeType) { ... }

那么你可以这样做:

for x in &mut data { transform(x) }

其他解决方案会很笨拙,因为它们需要处理 transform 可能会崩溃的事实。

关于rust - 是否可以在不分配新 Vec 的情况下将函数映射到 Vec 上?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41832050/

相关文章:

syntax - 匹配借用的枚举——为什么这个语法是等价的?

rust - 如何从 Rust 调用内置的 Dyon 函数?

rust - 如何匹配任意位置的多个字节?

rust - 发送到数组中的每个 futures::sync::mpsc::Sender

rust - 如何确保对象的生命周期不会超过其工厂

rust - 在 while 循环中更新可变 HashMap

rust - 为什么这些场景会编译并创建悬挂指针?

rust - 如何提供默认的 Debug 实现?

rust - 将次要功能添加到需要新依赖项的 crate 的选项

rust - 为什么从 Rust 中的函数返回一个 &[u8] 而不是 u8 借用自己?