使用泛型和函数指针克隆结构时如何修复 "the method `clone` exists but the following trait bounds were not satisfied"?
How do I fix "the method `clone` exists but the following trait bounds were not satisfied" when cloning a struct with generics and a function pointer?
我正在编写一个将在终端中创建菜单界面的函数。要使用该函数,需要传递一个 Vec<menu_option>
#[derive(Clone)]
pub struct menu_option<'a, T> {
pub command: &'a str,
pub description: &'a str,
pub action: menu_option_action<'a, T>,
}
#[derive(Clone)]
pub enum menu_option_action<'a, T> {
sub_menu(Vec<menu_option<'a, T>>),
callback(fn(state: T) -> T),
leave,
}
我在设计菜单的时候,可以有多个层次,可以有一个menu_action
的重复。即每一层都有一个"leave"/"return":
// In my actual code I construct a vector of `menu_option`s
fn example() {
type StateType = i32;
let mut state: StateType = 88;
let leave_option: menu_option<&mut StateType> = menu_option::<&mut StateType> {
command: "l",
description: "leave",
action: menu_option_action::leave,
};
let a = leave_option.clone();
}
error[E0599]: no method named `clone` found for struct `menu_option<'_, &mut i32>` in the current scope
--> src/lib.rs:24:26
|
2 | pub struct menu_option<'a, T> {
| -----------------------------
| |
| method `clone` not found for this
| doesn't satisfy `menu_option<'_, &mut i32>: std::clone::Clone`
...
24 | let a = leave_option.clone();
| ^^^^^ method not found in `menu_option<'_, &mut i32>`
|
= note: the method `clone` exists but the following trait bounds were not satisfied:
`&mut i32: std::clone::Clone`
which is required by `menu_option<'_, &mut i32>: std::clone::Clone`
= help: items from traits can only be used if the trait is implemented and in scope
= note: the following trait defines an item `clone`, perhaps you need to implement it:
candidate #1: `std::clone::Clone`
我该如何解决这个问题?
我尝试在线搜索但找不到解决方案,至少没有找到适合我的解决方案(我认为我找到的是旧的 Rust)
我不知道是什么阻止了克隆,因为 T
类型的唯一用途是我认为可以克隆的函数指针。
当您在 menu_option
和 menu_option_action
上自己实施 Clone
时,它会起作用。默认情况下,由于您的 struct/enum 具有类型参数,因此 #[derive(Clone)]
属性的宏扩展会将您的类型的克隆实现限制为 T: Clone
.
在您的情况下,不仅不需要此要求,而且也不太可能得到尊重(例如 &mut T
未实施 Clone
)。通过手动实施 Clone
,您可以摆脱 T: Clone
要求并且它有效!
请注意,函数指针实现了 Copy
,这就是 menu_option_action::callback(*f)
起作用的原因:
type StateType = i32;
pub struct menu_option<'a, T> {
pub command: &'a str,
pub description: &'a str,
pub action: menu_option_action<'a, T>,
}
impl<'a, T> Clone for menu_option<'a, T> {
fn clone(&self) -> Self {
menu_option {
command: self.command.clone(),
description: self.description.clone(),
action: self.action.clone(),
}
}
}
pub enum menu_option_action<'a, T> {
sub_menu(Vec<menu_option<'a, T>>),
callback(fn(T) -> T),
leave,
}
impl<'a, T> Clone for menu_option_action<'a, T> {
fn clone(&self) -> Self {
match self {
menu_option_action::sub_menu(sub) => menu_option_action::sub_menu(sub.to_vec()),
menu_option_action::callback(f) => menu_option_action::callback(*f),
menu_option_action::leave => menu_option_action::leave,
}
}
}
fn main() {
let mut state: StateType = 88;
let leave_option: menu_option<&mut StateType> = menu_option {
command: "l",
description: "leave",
action: menu_option_action::leave,
};
let a = leave_option.clone();
}
我正在编写一个将在终端中创建菜单界面的函数。要使用该函数,需要传递一个 Vec<menu_option>
#[derive(Clone)]
pub struct menu_option<'a, T> {
pub command: &'a str,
pub description: &'a str,
pub action: menu_option_action<'a, T>,
}
#[derive(Clone)]
pub enum menu_option_action<'a, T> {
sub_menu(Vec<menu_option<'a, T>>),
callback(fn(state: T) -> T),
leave,
}
我在设计菜单的时候,可以有多个层次,可以有一个menu_action
的重复。即每一层都有一个"leave"/"return":
// In my actual code I construct a vector of `menu_option`s
fn example() {
type StateType = i32;
let mut state: StateType = 88;
let leave_option: menu_option<&mut StateType> = menu_option::<&mut StateType> {
command: "l",
description: "leave",
action: menu_option_action::leave,
};
let a = leave_option.clone();
}
error[E0599]: no method named `clone` found for struct `menu_option<'_, &mut i32>` in the current scope
--> src/lib.rs:24:26
|
2 | pub struct menu_option<'a, T> {
| -----------------------------
| |
| method `clone` not found for this
| doesn't satisfy `menu_option<'_, &mut i32>: std::clone::Clone`
...
24 | let a = leave_option.clone();
| ^^^^^ method not found in `menu_option<'_, &mut i32>`
|
= note: the method `clone` exists but the following trait bounds were not satisfied:
`&mut i32: std::clone::Clone`
which is required by `menu_option<'_, &mut i32>: std::clone::Clone`
= help: items from traits can only be used if the trait is implemented and in scope
= note: the following trait defines an item `clone`, perhaps you need to implement it:
candidate #1: `std::clone::Clone`
我该如何解决这个问题?
我尝试在线搜索但找不到解决方案,至少没有找到适合我的解决方案(我认为我找到的是旧的 Rust)
我不知道是什么阻止了克隆,因为 T
类型的唯一用途是我认为可以克隆的函数指针。
当您在 menu_option
和 menu_option_action
上自己实施 Clone
时,它会起作用。默认情况下,由于您的 struct/enum 具有类型参数,因此 #[derive(Clone)]
属性的宏扩展会将您的类型的克隆实现限制为 T: Clone
.
在您的情况下,不仅不需要此要求,而且也不太可能得到尊重(例如 &mut T
未实施 Clone
)。通过手动实施 Clone
,您可以摆脱 T: Clone
要求并且它有效!
请注意,函数指针实现了 Copy
,这就是 menu_option_action::callback(*f)
起作用的原因:
type StateType = i32;
pub struct menu_option<'a, T> {
pub command: &'a str,
pub description: &'a str,
pub action: menu_option_action<'a, T>,
}
impl<'a, T> Clone for menu_option<'a, T> {
fn clone(&self) -> Self {
menu_option {
command: self.command.clone(),
description: self.description.clone(),
action: self.action.clone(),
}
}
}
pub enum menu_option_action<'a, T> {
sub_menu(Vec<menu_option<'a, T>>),
callback(fn(T) -> T),
leave,
}
impl<'a, T> Clone for menu_option_action<'a, T> {
fn clone(&self) -> Self {
match self {
menu_option_action::sub_menu(sub) => menu_option_action::sub_menu(sub.to_vec()),
menu_option_action::callback(f) => menu_option_action::callback(*f),
menu_option_action::leave => menu_option_action::leave,
}
}
}
fn main() {
let mut state: StateType = 88;
let leave_option: menu_option<&mut StateType> = menu_option {
command: "l",
description: "leave",
action: menu_option_action::leave,
};
let a = leave_option.clone();
}