我想知道您是否可以拥有一个包含具有不同模板参数的对象的容器。
我正在努力实现这样的目标:
#include <iostream>
#include <list>
template <class T>
class base
{
public:
T val;
base(T newVal): val(newVal) {};
};
class derived : public base<int>
{
public:
derived(int newVal): base(newVal) {};
};
int main ( void )
{
std::list < base<?> > base_collection;
return 0;
}
我希望我当前的项目尽可能灵活和动态,当需要新的派生类时几乎不需要额外的编码,并且我当前的实现使得这样一个列表的存在非常重要。
是否有一种常用的、有益的、干净的方法来实现这一目标?
一个可能的实现是使用双重调度:
#include <iostream>
#include <list>
struct visitor;
struct dispatchable {
virtual void accept(visitor &v) = 0;
};
template <class>
struct base;
struct visitor {
template<typename T>
void visit(base<T> &);
};
template <class T>
struct base: dispatchable {
T val;
base(T newVal): val(newVal) {};
void accept(visitor &v) override { v.visit(*this); }
};
struct derivedInt : base<int> {
derivedInt(int newVal): base(newVal) {};
};
struct derivedDouble : base<double> {
derivedDouble(double newVal): base(newVal) {};
};
template<>
void visitor::visit(base<int> &) {
std::cout << "int" << std::endl;
}
template<>
void visitor::visit(base<double> &) {
std::cout << "double" << std::endl;
}
int main ( void ) {
visitor v{};
std::list <dispatchable*> coll;
coll.push_back(new derivedInt{42});
coll.push_back(new derivedDouble{.42});
for(auto d: coll) d->accept(v);
}
这样,您只需定义处理新的专门函数base<T>
您想要介绍的类型。
举个例子,如果你想使用base<char>
,你必须定义:
template<>
void visitor::visit(base<char> &) {
std::cout << "char" << std::endl;
}
请注意,我假设您想要对待每个专业化base<T>
以不同的方式。否则,定义通用成员函数就足够了visitor::visit
并放弃专业。
旁注:不要使用裸指针。
这是一个例子。在生产代码中,我会使用智能指针。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)