保留旧问题。请参见以下解决方案。 这可能是一些简单的东西,但仍然存在问题。我有以下C++11代码片段:
#include <vector>
template <typename... Ts>
struct typelist
{
};
template <typename T>
struct EventContainer
{
typedef T Type;
/// TODO. Ring buffer
std::vector<T> container;
void push(const T& t)
{
EventContainer<T>::container.push_back(t);
}
virtual ~EventContainer()
{
}
};
template <template <typename...> class TL>
class EventStorage:
public EventContainer<Ts>...
{
};
class Event1
{
};
class Event2
{
};
typedef typelist<Event1,Event2> Events12;
int main()
{
EventStorage<Events12> ev;
return 0;
}
我该如何让
EventStorage
继承 typelist
中每个类型所模板化的 EventContainer
呢?我知道可以使用 Loki 库,但我想使用 C++11 的可变参数模板来实现。
谢谢。解决方案1:修复
EventStorage
模板模板问题。这将使得 EventStorage
多重继承所有用 Ts
模板化的 EventContainer
类型。template <typename...>
class EventStorage
{
};
template <typename... Ts>
class EventStorage < typelist<Ts...> >:
public EventContainer<Ts>...
{
};
现在我遇到了编译时错误,出现在以下的main()
函数中:
int main()
{
EventStorage<Events12> ev;
Event1 ev1;
ev.push(ev1);
return 0;
}
In function ‘int main()’:
error: request for member ‘push’ is ambiguous
error: candidates are: void EventContainer<T>::push(const T&) [with T = Event2]
error: void EventContainer<T>::push(const T&) [with T = Event1]
为什么编译器会混淆?毕竟我使用了特定类型的推送。这里是GCC 4.6.1。
解决方案2:
正如@Matthieu M.建议的那样,我可以在EventStorage
中提供一个转发方法,但这将付出一个额外的函数调用的代价:
template <typename T>
void push(const T& t)
{
EventContainer<T>::push(t);
}
据Alexandrescu所说,只要参数是引用,编译器就会优化这个前向调用。现在问题已经正式关闭 :)
typedef typelist<Event1,Event2> pumpEvents;
typedef typelist<Event3,Event4,Event5> displayEvents;
但是按照您所说的方式,如果需要同时存储它们两个,我想要将这两个“类型列表(typelists)”组合起来。 - Dragomir Ivanovtypelist
适配器和一个存储组合器。 - Matthieu M.push()
不是被重载了吗? - Dragomir Ivanov