Ric*_*ann 0 code-duplication pattern-matching rust
我已经使用clap
.
在其中,我有几个结构体和枚举,其中包含特定子命令的这些结构体。
我现在遇到了某种类型的代码重复问题,想知道 Rust 语言是否有一些我不知道的功能可以消除重复。
这是一个 MRE:
pub trait Runner {
fn run(&self);
}
pub struct Foo;
impl Runner for Foo {
fn run(&self) {
println!("Fooing");
}
}
pub struct Bar;
impl Runner for Bar {
fn run(&self) {
println!("Baring");
}
}
pub enum Action {
DoFoo(Foo),
DoBar(Bar),
}
impl Runner for Action {
fn run(&self) {
match self {
Self::DoFoo(runner) => runner.run(),
Self::DoBar(runner) => runner.run(),
}
}
}
Run Code Online (Sandbox Code Playgroud)
正如您所看到的,模式匹配<Action as Runner>::run()
在所有变体上都具有几乎相同的代码,因为所有枚举变体的元组都包含一个实现Runner
.
在这个 MRE 中,这非常简单,但我的实际代码目前有七个变体。
Rust 是否可以消除重复的模式匹配并利用所有变体都包含具有相同特征的结构这一事实?
当尝试使用枚举模拟动态调度方法(依赖于dyn
特征)时,enum_dispatch
板条箱会自动执行样板文件,以便系统地转发特征中的每个方法。
这是一个基于您的简单示例。
#[enum_dispatch]
用于您打算为许多类型实现的特征。
#[enum_dispatch(Runner)]
指示以下枚举,其每个变体都是实现此特征的类型,然后为所有这些变体自动生成每个特征方法的转发,就像您手动执行的那样(每个方法都是考虑match
所有变体的语句,以便转接呼叫)。
use enum_dispatch::enum_dispatch;
#[enum_dispatch]
pub trait Runner {
fn run(&self);
}
pub struct Foo;
impl Runner for Foo {
fn run(&self) {
println!("Fooing");
}
}
pub struct Bar;
impl Runner for Bar {
fn run(&self) {
println!("Baring");
}
}
#[enum_dispatch(Runner)]
pub enum Action {
Foo,
Bar,
}
fn main() {
let actions = [
Action::from(Foo {}),
Action::from(Bar {}),
Action::from(Bar {}),
Action::from(Foo {}),
];
for a in actions.iter() {
a.run();
}
}
/*
Fooing
Baring
Baring
Fooing
*/
Run Code Online (Sandbox Code Playgroud)