首页 > 解决方案 > 将模块存储为 rust 中的变量

问题描述

我有 2 个不同的模块,它们具有完全相同的实现、相同的功能、类型等。它们只是做不同的事情。我希望能够在运行时选择其中一个模块并专门使用它。此外,根据平台、功能等,在编译时可能存在也可能不存在这些模块中的几个。是我想要的超级精简版本的链接。我正在尝试在各种gfx-hal之间进行选择后端。我能想到的最好的方法是一个宏,它为每个可能的模块创建一个 if 语句,然后在模块中的函数运行时触发该 if 语句。然而,这看起来并不优雅或一点也不好。那么有没有办法将模块存储在一个变量中并访问它,或者有什么方法可以模仿它?

提前致谢

标签: rust

解决方案


您可以通过将每个模块转换为自己的特征实现来做到这一点,类似于gfx-rs事情的方式。

你的 " trait" 实际上永远不会用状态来实现,而是一个相关项目的集合,比如函数、其他类型等。

你可以像这样打包它:

#![allow(dead_code)]
mod foo {
    pub fn print() { println!("hello from foo") }
}

mod bar {
    pub fn print() { println!("hello from bar"); }
}

mod zam { // this may not exist depending on the platform, one will always exist
    pub fn print() { println!("hello from zam"); }
}

struct FOO;
struct BAR;
struct ZAM;

trait RuntimeModule {
    fn print();
}

impl RuntimeModule for FOO {
    fn print() { foo::print(); }
}

impl RuntimeModule for BAR {
    fn print() { bar::print(); }
}

impl RuntimeModule for ZAM {
    fn print() { zam::print(); }
}

fn main() {
    // Here we decide which to use
    print_module::<FOO>();
}
// This is our "entrypoint"
fn print_module<T: RuntimeModule>() {
    T::print();
}

如果我们决定在运行时使用哪个(在本例中main),我们可以调用一个通用函数,该函数将使用相关的类型/函数来做出决定。

请注意,如果每个实现包含不同的关联类型,您将无法使用。Box<dyn RuntimeModule>RuntimeModule


推荐阅读