【发布时间】:2012-10-03 15:58:27
【问题描述】:
基本上,我正在尝试编写一个包含通用迭代器的基类。
显然模板虚函数不起作用,这就是我尝试 boost::any 的原因,但它仍然没有重载 Iterator 的 get() 方法(它不断抛出下面定义的异常)。我似乎也无法将其设为纯虚拟,因为编译器抱怨“虚拟迭代器 begin() = 0;” (它说“无法创建抽象类迭代器的实例”)。
我有非常具体的限制,我必须/想要遵守,因此可能会考虑问题的替代解决方案,但可能无法使用。
下面是部分代码:
template <class T, class C>
class Iterator
{
public:
virtual T& operator*() { T *t = boost::any_cast<T>(&get()); return *t; };
virtual boost::any& get() { throw new Exception("get not overridden!!"); };
//virtual boost::any& get() = 0;
protected:
C::iterator iter;
};
template <class T>
class VectorIterator: public Iterator<T, std::vector<T> >
{
public:
VectorIterator(std::vector<T>::iterator iterator): Iterator<T, std::vector<T> >(iterator) { };
virtual boost::any& get() { return *iter; };
};
template <class Value, class Container>
class Repository
{
public:
typedef Iterator<Value, Container> iterator;
virtual iterator begin() = 0;
virtual iterator end() = 0;
};
class SomeRepository : public Repository<RandomClass, std::vector<RandomClass> >
{
public:
iterator begin() { return VectorIterator<RandomClass>(items.begin()); };
iterator end() { return VectorIterator<RandomClass>(items.end()); };
}
那么,为什么它不起作用以及(如何)我可以修复它?
PS:我知道这与另一个问题非常相似,但我无法将其完全放入评论中,并且真的不知道我还能把它放在哪里。
更新:
所以我设法通过让 get() 返回一个 void (eww) 指针并忘记 boost::any 来解决一些问题。但它仍然调用 Iterator::get 而不是 VectorIterator::get (这是我最初的问题)(当我尝试使用 *someRepository.begin() 之类的东西时),有人知道为什么吗?
【问题讨论】:
-
我很好奇。这应该达到什么目的?如果您想在迭代器上键入擦除,则可以使用更好的方法。
-
throw new Exception(...);-- 请不要... -
@pmr 我们的代码中存在迭代存储库的所有元素的现有功能,我认为更好的方法是为此使用通用迭代器。
-
@Dukeling 如果你真的需要一个类型擦除的迭代器(你可能不需要),你应该看看thbecker.net/free_software_utilities/… 不过你可能不需要它。
-
你有错误的原因是你返回
Iterator,这是抽象的。 C++ 是一种与例如语言大不相同的语言。 C# 或 Java(它们在语法上可能表面上相似,但仅此而已)。返回Iterator只会返回动态类型的值Iterator。
标签: c++ templates inheritance boost virtual