如何实现具有多个开关的工厂? [英] How to implement a factory with multiple switches?

查看:56
本文介绍了如何实现具有多个开关的工厂?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想实现用于创建对象的工厂功能.我的对象模板如下所示:

I want to implement a factory function for creating objects. My object template looks like this:

template <typename TA, typename TB>
struct MyImpl : public MyInterface
{
    // content
};

我的工厂是这样的:

MyInterface* factory(char ta, char tb)
{
    if(ta == 'c' && tb == 'c')
    {
        return new MyImpl<char, char>();
    }
    if(ta == 'c' && tb == 's')
    {
        return new MyImpl<char, short>();
    }
    if(ta == 's' && tb == 'c')
    {
        return new MyImpl<short, char>();
    }
    // and so on ....
}

工厂函数必须接受非静态char数据(tatb),因为在编译时无法确定它,我想这就是工厂的全部内容.实际上,tatb是从文件(或网络)中读取的.

The factory function must accept non-static char data (ta, tb) for it could not be determined at compile time, and I think that's the whole point of this factory. In fact, ta and tb are read from a file (or network).

我想要一个更简单的解决方案来避免烦人的2级切换.

I want a simpler solution to avoid the annoying 2-level switch.

我认为我的问题类似于除了不能使用静态参数外,如何在C中编写一个元数据.

I think my question is similar to how-would-one-write-a-meta-if-else-if-in-c with the exception that I cannot use static parameters.

也许我应该回退到C宏并使用一些宏技巧来缩小当前代码?

Perhaps I should just fallback to C macros and use some macro tricks to shrink my current code?

提前谢谢!

更新

回答@Rob:

我的实际代码会包含很多其他内容,变得更加复杂,并且难以阅读,并且在很多方面都没有关系.我正在尝试使伪代码正确,如果有任何问题,请告诉我:-).

My actual code would be more complex with many other stuffs in it and harder to read and not related in many aspects. I'm trying to get the pseudo-code right, If there is any problem, please kindly inform me :-).

@Dynguss的答案:

Answer to @Dynguss:

我的问题是,在我的实际实现中,工厂的参数(ta,tb)的范围会很大,例如10 X ta和20 X tb,并且ta和tb的组合在行中会很长,并且很难维护.因此,我至少需要某种方法来简化组合工作.

My problem is that in my actual implementation, parameters of the factory (ta, tb) would be large in range, like 10 X ta and 20 X tb, and combination of ta and tb would be very long in lines, and hard to maintain. So I need at least some way to ease the combination efforts.

推荐答案

这是个主意:

template <typename T>
MyInterface * factroy(char t)
{
    if (t == 'c') { return MyImpl<T, char>();  }
    if (t == 's') { return MyImpl<T, short>(); }
    // ...
}

MyInterface * factory(char ta, char tb)
{
    if (ta == 'c') { return factroy<char>(tb);  }
    if (ta == 's') { return factroy<short>(tb); }
    // ...
}

使用可变参数模板,此模式可以扩展为任意数量的类型参数–例如:

With variadic templates, this pattern could be extended to any number of type arguments – for example:

struct Base { virtual ~Base() = default; };
template <typename A, typename B, typename C> struct Foo : Base { };

#include <tuple>

template <typename ...Args>
constexpr Base * factory(std::tuple<Args...>)
{
    return new Foo<Args...>;
}

template <typename ...Args, typename ...Char>
constexpr Base * factory(std::tuple<Args...>, char t, Char ... ts)
{
    return t == 'c' ? make(std::tuple<char,      Args...>(), ts...)
         : t == 's' ? make(std::tuple<short int, Args...>(), ts...)
         : t == 'i' ? make(std::tuple<int,       Args...>(), ts...)
         : t == 'l' ? make(std::tuple<long int,  Args...>(), ts...)
         : nullptr;
}

用法:auto p = factory(std::tuple<>(), 'c', 's', 'l');

这篇关于如何实现具有多个开关的工厂?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆