我想创建两个特征,SaveSource
和 SaveDestination
,这样当某些类型实现这些特征时,函数:
fn save(a, b)
必须为所有 a : SaveSource
和 b : SaveDestination
实现(并且当新类型添加到 SaveSource
或 SaveDestination
,它必须为所有现有的 SaveDestination
或 SaveSource
实现 save
函数。
这样的事情有可能吗?如果没有,我可以使用什么来获得相同的结果吗?
最佳答案
当 A
和 B
的某些组合未实现 save
时,您不能强制编译器发出错误。但是您可以拥有一个通用函数,该函数要求它接收的特定 A
和 B
的组合实现保存
。
为此,我们需要将 save
包装在一个特征中,并在包含 A
和 B
的某种类型上实现它;最简单的选择是元组。 (不过,如果特征和类型不在同一个 crate 中,一致性可能会妨碍。)
trait Save {
fn save(self);
}
struct Foo; // sample save source
struct Bar; // sample save destination
// save is defined for the combination of `Foo` and `Bar`
impl Save for (Foo, Bar) {
fn save(self) {
unimplemented!()
}
}
// in order to call this, the type `(A, B)` must implement `Save`
fn call_save<A, B>(a: A, b: B)
where
(A, B): Save
{
(a, b).save();
}
fn main() {
// this call compiles because `impl Save for (Foo, Bar)` is present
call_save(Foo, Bar);
}
你也可以做引用:
trait Save {
fn save(self);
}
struct Foo;
struct Bar;
impl<'a, 'b> Save for (&'a Foo, &'b Bar) {
fn save(self) {
unimplemented!()
}
}
fn call_save<'a, 'b, A, B>(a: &'a A, b: &'b B)
where
(&'a A, &'b B): Save
{
(a, b).save();
}
fn main() {
call_save(&Foo, &Bar);
}
关于rust - 定义两个特征,使得实现它的两组类型的笛卡尔积必须存在一个函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44314403/