Как реализовать черту для итераторов над разработчиками этой черты - PullRequest
1 голос
/ 31 октября 2019

Скажем, у меня есть черта Intersectable, которая реализована для различных геометрических примитивов. Я хочу реализовать Intersectable для итераторов по списку этих примитивов.

У меня есть код ( детская площадка ):

use std::borrow::Borrow;

struct Ray {}
trait Intersectable {
    fn intersect(self, ray: &Ray) -> bool;
}

struct Circle {}
impl Intersectable for Circle {
    fn intersect(self, _ray: &Ray) -> bool {
        true
    }
}
impl Intersectable for &Circle {
    fn intersect(self, _ray: &Ray) -> bool {
        true
    }
}

impl<'a, T> Intersectable for T
    where T: Iterator<Item = &'a dyn Intersectable> {
    fn intersect(self, ray: &Ray) -> bool {
        for obj in self {
            if obj.intersect(ray) {        // Error occurs here
                return true;
            }
        }
        return false;
    }
}

fn main() {
    let objects: [Box<dyn Intersectable>; 2] = [
        Box::new(Circle {}),
        Box::new(Circle {}),
    ];
    let ray = Ray {};

    // I wish to call intersect on the iterator as follows:
    println!("Intersection: {}", objects.iter().map(|b| b.borrow()).intersect(&ray));
}

Это приводит к ошибке:

error[E0161]: cannot move a value of type dyn Intersectable: the size of dyn Intersectable cannot be statically determined
  --> src/main.rs:24:16
   |
24 |             if obj.intersect(ray) {
   |                ^^^

error[E0507]: cannot move out of `*obj` which is behind a shared reference
  --> src/main.rs:24:16
   |
24 |             if obj.intersect(ray) {
   |                ^^^ move occurs because `*obj` has type `dyn Intersectable`, which does not implement the `Copy` trait

Чтобы исправить это, я попытался заменить ошибочный вызов intersect на <T::Item>::intersect(obj, ray) и добавить следующую реализацию ( детская площадка ):


impl Intersectable for &dyn Intersectable {
    fn intersect(self, ray: &Ray) -> bool {
        (*self).intersect(ray)             // Error now occurs here
    }
}

Я получаю ту же ошибку в новом коде. Еще одна попытка дала error[E0119]: conflicting implementations of trait, так как я пытался реализовать ее для ссылочного типа.

Так можно ли реализовать Intersectable для Iterator<Item = &dyn Intersectable>?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...