rust - 合并盒装元素

标签 rust

假设存在以下函数:

fn merge(a1: A, a2: A) -> A { /* implemented */ }

有没有办法使用盒装类型为相同的操作编写函数?即:

fn boxed_merge(a1: Box<A>, a2: Box<A>) -> Box<A> { /* ??? */ }

最佳答案

我提倡按值 merge 应该作为您的基本实现。相反,变异方法提供了更大的灵 active 。然后,您可以在此基础上构建按值和按装箱值方法:

struct A(u8);

impl A {
    fn merge_ref(&mut self, other: &A) {
        self.0 += other.0
    }
}

fn merge(mut a1: A, a2: A) -> A { 
    a1.merge_ref(&a2);
    a1
}

fn boxed_merge(mut a1: Box<A>, a2: Box<A>) -> Box<A> {
    a1.merge_ref(&a2);
    a1
}

fn main() {
    let a1 = A(1);
    let a2 = A(2);

    let a3 = merge(a1, a2);

    let boxed_a3 = Box::new(a3);
    let boxed_a4 = Box::new(A(4));

    let boxed_a7 = boxed_merge(boxed_a3, boxed_a4);

    println!("{}", boxed_a7.0);
}

值得注意的是,这在盒装情况下会更有效,因为您不必执行任何额外的分配。

As oli_obk - ker points out :

This only applies for merges of Copy structures. If you had two sets that are merged, the elements of the set might not be copyable

这可以通过在 merge_ref 中按值合并并使用相同的技巧在 boxed_merge 方法中移出盒子来解决:

struct B(Vec<u8>);

impl B {
    fn merge_ref(&mut self, other: B) {
        self.0.extend(other.0)
    }
}

fn merge(mut b1: B, b2: B) -> B { 
    b1.merge_ref(b2);
    b1
}

fn boxed_merge(mut b1: Box<B>, b2: Box<B>) -> Box<B> {
    b1.merge_ref(*b2);
    b1
}

fn main() {
    let b1 = B(vec![1]);
    let b2 = B(vec![2]);

    let b3 = merge(b1, b2);

    let boxed_b3 = Box::new(b3);
    let boxed_b4 = Box::new(B(vec![4]));

    let boxed_b7 = boxed_merge(boxed_b3, boxed_b4);

    println!("{:?}", boxed_b7.0);
}

我们这里仍然没有任何额外的分配。

关于rust - 合并盒装元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44018378/

相关文章:

Rust "expected type"错误打印完全相同的不匹配类型

regex - Rob Pikes 正则表达式的惯用 Rust 重写

rust - 列出范围内由类型实现的所有特征

rust - 从函数返回 future 流

memory - 为什么Rust中的打印内存地址同时包含40位和48位地址?

rust - 如何解析基于 LLVM MCJIT 的 JIT 中的当前进程符号?

rust - 将二维固定大小的数组转换为切片

Rust 函数没有静态生命周期?

rust - 如何使用 html5ever 解析页面、修改 DOM 并序列化它?

rust - 为什么 solicit 0.4.4 尝试使用 openssl 0.9.12,即使我的 Cargo.toml 中有 openssl 0.7.14?