我有任务写自己的容器Linked_list和Array_list.我有一个接口:
typedef int value_type; class Container { public: class Iterator { public: Iterator(); Iterator(value_type* other); Iterator(const Iterator& other); Iterator& operator=(const Iterator& other); ... }; Container(); Container(const Container& other); ~Container(); virtual value_type& front() const=0; virtual value_type& back() const=0; virtual Iterator begin() const=0; // ... };
我做派生类Linked_list和Array_list:
class Linked_list:public Container { public: long int cur_size; List elem; static Link end_; class Iterator: public Container::Iterator { friend Linked_list; Link *p; }; Iterator begin() const; //overriding virtual function return type differs ... ... }
我认为这是错的.应该嵌套类Linked_list :: Iterator是派生类吗?
是否可以这样做,如果我不能更改界面?
解决方法
考虑到您不能使用模板的设计约束,而不是一件事情应该改变:添加接口IteratorImpl.因此,您可以使类Iterator从基类Container非虚拟.它需要是非虚拟的,因为STL相似的迭代器应该具有值语义.参见
pimpl idiom了解更多细节如何工作!
喜欢这个:
typedef int value_type; class Container { protected: class IteratorImpl { public: virtual void next() = 0; virtual IteratorImpl* clone() const = 0; virtual value_type get() const = 0; virtual bool isEqual(const IteratorImpl& other) const = 0; }; public: class Iterator { public: Iterator(IteratorImpl* impl) : impl(impl) {} ~Iterator() { delete impl; } Iterator(const Iterator& other) : impl(other.impl->clone()) {} Iterator& operator=(const Iterator& other) { IteratorImpl* oldImpl = impl; impl = other.impl->clone(); delete oldImpl; } bool operator == (const Iterator& other) const { return impl->isEqual(*other->impl); } Iterator& operator ++ () { impl->next(); return *this; } value_type& operator*() const { return impl->get(); } value_type* operator->() const { return &impl->get(); } }; Container(); Container(const Container& other); ~Container(); virtual value_type& front() const=0; virtual value_type& back() const=0; virtual Iterator begin() const=0; // ... };
然后在你的派生只是实现IteratorImpl:
class Linked_list:public Container { protected: class IteratorImpl: public Container::IteratorImpl { .... }; public: Iterator begin() const { return new IteratorImpl(firstNode); } Iterator end() const { return new IteratorImpl(nodeAfterLastNode); } ... };
这些firstNode和nodeAfterLastNode只是我的猜测 – 使用任何你需要实现IteratorImpl接口…