Я пытаюсь клонировать вектор в штучной упаковке.
Естественно, просто получить Clone
на всех структурах, которые реализуют мою черту, недостаточно, потому что компилятор не знает во время компиляции, что все структуры, реализующие черту, имеют Clone
.
Хорошо, тогда я попытался использовать Clone
в качестве супертрейта, но это привело к ошибке в названии. Я в недоумении для решений.
Вот минимальная рабочая реализация (или не работает, так как я не могу клонировать)
#![allow(dead_code, unused_macros)]
use std::fmt::Debug;
trait MusicElement: Debug + Clone {
fn duration(&self) -> f32;
}
#[derive(Debug, Clone)]
struct Note<'a> {
name: &'a str,
duration: f32,
}
impl<'a> MusicElement for Note<'a> {
fn duration(&self) -> f32 {
self.duration
}
}
#[derive(Debug, Clone)]
struct Pause {
duration: f32,
}
impl MusicElement for Pause {
fn duration(&self) -> f32 {
self.duration
}
}
#[derive(Debug, Clone)]
struct Sequence {
elements: Vec<Box<MusicElement>>,
}
impl MusicElement for Sequence {
fn duration(&self) -> f32 {
self.elements.iter().map(|e| e.duration()).sum()
}
}
fn main() {
let a4 = |dur| Box::new(Note { name: "a4", duration: dur });
let seq = Sequence { elements: vec![a4(0.25), a4(0.25), a4(0.5)] };
println!("{:?}", seq);
let seq2 = seq.clone();
println!("{:?}", seq2);
}
С этой ошибкой:
error[E0038]: the trait `MusicElement` cannot be made into an object
--> src/main.rs:33:5
|
33 | elements: Vec<Box<MusicElement>>,
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `MusicElement` cannot be made into an object
|
= note: the trait cannot require that `Self : Sized`
А вот ссылка на игровую площадку для удобства выполнения кода.
Я также пытался сделать вектор elements
в Sequence
a Vec<Box<MusicElement + Clone>>
, но это тоже не сработало.
Мне не удалось найти каких-либо полезных решений в Интернете, поэтому вот мой вопрос: как сделать код клонируемым?