如何拆箱包含在多态向量中的元素? [英] How to unbox elements contained in polymorphic vectors?

查看:53
本文介绍了如何拆箱包含在多态向量中的元素?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

阅读这个对属于特征的对象的向量"的回答后,看起来 Rust 会自动拆箱.是这样吗?

After reading this answer to "Vector of objects belonging to a trait", it looks like Rust does automatic unboxing. Is this the case?

我的代码无法编译,我不明白该答案的代码是如何编译的.

My code doesn't compile and I don't understand how that answer's code could compile.

对包含装箱特征的多态向量的元素进行拆箱的正确方法是什么?

What is the correct way to unbox the elements of a polymorphic vector, one containing boxed traits?

我已经阅读了 Rust by ExampleBox 文档,我看不到任何看起来像的方法unbox().

I've read Rust by Example and the Box documentation and I can't see any method that looks like unbox().

我的代码是:

trait HasArea {
    fn area(&self) -> f64;
}

struct Circle {
    x: f64,
    y: f64,
    radius: f64,
}

impl HasArea for Circle {
    fn area(&self) -> f64 {
        std::f64::consts::PI * (self.radius * self.radius)
    }
}

struct Square {
    x: f64,
    y: f64,
    side: f64,
}

impl HasArea for Square {
    fn area(&self) -> f64 {
        self.side * self.side
    }
}

fn print_area<T: HasArea>(shape: T) {
    println!("This shape has an area of {}", shape.area());
}

fn main() {
    let c = Circle {
        x: 0.0f64,
        y: 0.0f64,
        radius: 1.0f64,
    };

    let s = Square {
        x: 0.0f64,
        y: 0.0f64,
        side: 1.0f64,
    };

    print_area(c);
    print_area(s);

    let vec: Vec<Box<HasArea>> = Vec::new();
    vec.push(Box::new(c));
    vec.push(Box::new(s));

    for x in vec {
        print_area(x)
    }
}

我的错误是:

   Compiling rustgraph v0.1.0 (file:///home/chris/lunch/rustgraph)
error[E0277]: the trait bound `Box<HasArea>: HasArea` is not satisfied
  --> src/main.rs:54:9
   |
54 |         print_area(x)
   |         ^^^^^^^^^^ the trait `HasArea` is not implemented for `Box<HasArea>`
   |
   = note: required by `print_area`

推荐答案

您可以像 print_area(*x) 一样取消引用它,但由于其他原因它不起作用:Sized 绑定 print_area 参数.您的函数需要知道其参数的大小.

You can dereference it like print_area(*x), but it won't work for other reasons: the Sized bound for the print_area argument. Your function needs to know the size of its arguments.

您的代码中还有其他问题:您试图推入一个不可变的向量,并且您试图将移动的值装箱.这些在您在 print_area() 中使用后被移动了.

You have other problems in your code: you are trying to push into an immutable vector and you are trying to box moved values. These were moved after you used it in print_area().

我的观点是让 print_area 成为一个接受不可变引用的方法会更容易.这将按您的预期工作.

My opinion is that it would be easier to make print_area a method which takes an immutable reference. This will work as you expected.

trait HasArea {
    fn area(&self) -> f64;
    fn print_area(&self) {
        println!("This shape has area of {}", self.area());
    }
}

struct Circle {
    x: f64,
    y: f64,
    radius: f64,
}

impl HasArea for Circle {
    fn area(&self) -> f64 {
        std::f64::consts::PI * (self.radius * self.radius)
    }
}

struct Square {
    x: f64,
    y: f64,
    side: f64,
}

impl HasArea for Square {
    fn area(&self) -> f64 {
        self.side * self.side
    }
}

fn print_area<T: HasArea>(shape: &T) {
    println!("This shape has an area of {}", shape.area());
}

fn main() {
    let c = Circle {
        x: 0.0f64,
        y: 0.0f64,
        radius: 1.0f64,
    };

    let s = Square {
        x: 0.0f64,
        y: 0.0f64,
        side: 1.0f64,
    };

    c.print_area();
    s.print_area();

    let mut vec: Vec<Box<HasArea>> = Vec::new();
    vec.push(Box::new(c));
    vec.push(Box::new(s));

    for x in vec {
        x.print_area();
    }
}

这篇关于如何拆箱包含在多态向量中的元素?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆