Rust架构模式,在哈希图中存储多个工厂

问题描述 投票:0回答:1

我希望能够在单个哈希图中存储多个工厂,以便稍后将它们添加到工厂中(例如,通过插件),然后在应用程序中通过键名获得每个工厂(这是资源管理器。)>]

问题是通用的Fabric特性,Fabric可以创建不同类型的水果,但是我需要在HashMap<String, Box<dyn Fabric>>中指定一些内容,例如HashMap<String, Box<Fabric<Apple>>>HashMap<String, Box<Fabric<T>>>,它们也不有用,因为正如我所说,可以创造出完全不同的水果。

此外,我想foo​​方法可能还存在关于借用内容的问题。

那么您将如何实现这种“生锈方式”?

use std::collections::HashMap;

trait Fruit {
    fn get_name(&self) -> String;
}

trait Fabric<T: Fruit> {
    fn build(&self) -> Box<T>;
}

struct Banana {}
impl Fruit for Banana {
    fn get_name(&self) -> String { String::from("I'm banana") }
}

struct BananaFabric {}
impl Fabric<Banana> for BananaFabric  {
    fn build(&self) -> Box<Banana> {
        Box::new(Banana {})
    }
}

struct Apple {}
impl Fruit for Apple {
    fn get_name(&self) -> String { String::from("I'm apple") }
}

struct AppleFabric {}
impl Fabric<Apple> for AppleFabric  {
    fn build(&self) -> Box<Apple> {
        Box::new(Apple {})
    }
}

struct C {
    map: HashMap<String, Box<dyn Fabric>>,
}

impl C {
    pub fn new() -> C {
        C {
            map: HashMap::new()
        }
    }

    pub fn foo(&self, key: String) {
        match self.map.get(&key) {
            Some(&fabric) => {
                let fruit = fabric.build();
                println!("{}", fruit.get_name())
            },
            _ => println!("No fabric found")
        }
    }
}

fn main() {
    let c = C::new();
    c.foo(String::from("bar"));
}

我希望能够在单个哈希图中存储多个工厂,以便稍后将它们添加到工厂中(例如,通过插件),然后在应用程序中通过键名来获取每个工厂(这是资源管理器)...

design-patterns rust factory-pattern
1个回答
0
投票

你的意思是类似的>]

use std::collections::HashMap;

trait A {
    fn boo(&self) -> i32;
}

struct B {}

impl A for B {
    fn boo(&self) -> i32 {
        15
    }
}

struct C {
    map: HashMap<String, Box<dyn A>>,
}

impl C {
    pub fn new() -> C {
        C {
            map: HashMap::new(),
        }
    }

    pub fn foo(&self, key: String) {
        match self.map.get(&key) {
            Some(val) => println!("{}", val.boo()),
            _ => println!("None"),
        }
    }
}
fn main() {
    let mut c = C::new();

    c.map.insert(String::from("bar"), Box::new(B{}));

    c.foo(String::from("bar"));
}

© www.soinside.com 2019 - 2024. All rights reserved.