【发布时间】:2019-03-28 16:39:32
【问题描述】:
我在 C++ 中创建了一个链接列表,并希望为它实现一个迭代器,以便我可以进行范围循环:for (const int& i : list) where Linked_List<int> list;。
我的想法是创建 Iterator 作为 Linked_List 类的一部分,如下所示:
这是我目前得到的:
template <typename T>
class Linked_List
{
public:
struct Iterator;
struct Node;
public:
Linked_List();
~Linked_List() noexcept(false);
Linked_List(const Linked_List&) = delete;
Linked_List(Linked_List&&) = delete;
Linked_List& operator=(const Linked_List&) = delete;
Linked_List& operator=(Linked_List&&) = delete;
void push_back(T);
void push_front(T);
void pop_back();
void pop_front();
bool empty() const;
T back() const;
T front() const;
//void swap(T, T);
//void insert(Iterator, T);
//void erase(Iterator);
//Iterator begin() const;
//Iterator end() const;
private:
Node* head;
Node* tail;
};
template<typename T>
struct Linked_List<T>::Node
{
Node() : prev(nullptr), next(nullptr) {}
Node(T t) : value(t), prev(nullptr), next(nullptr) {}
Node* prev;
Node* next;
T value;
};
- 这是个好方法吗?
- 在增加列表以检查是否
current->next == tail时是否应该进行错误检查?如果是这样,我该怎么做?因为我的迭代器没有带尾的列表对象。
编辑:
我不确定如何实现struct Iterator;,我在弄清楚如何将它与列表连接时卡住了,以便我可以检查从迭代器返回的当前节点是否等于列表中的尾部,在 Linked_List @ 987654330@方法。
假设我已经为这样的迭代器实现了所有必要的运算符:
struct Iterator
{
T& operator*() const { return current->value; }
bool operator!=(const Iterator& rhs) { return (*_current != rhs._current); }
Iterator& operator++()
{
current = current->next;
return *this;
}
};
现在我将如何实施Iterator Linked_List<T>::begin() const; 和end()?
我想象一个虚构的用户制作这样的迭代器对象:
Linked_List<int>::Iterator it;
一个想法是有一个不带参数的公共构造函数和一个将节点作为参数的私有构造函数,_current 将被设置为,并有 Linked_List 类作为朋友。
【问题讨论】:
-
1/ 没关系。如果您最终得到多个具有类似迭代器实现的容器,那么可能值得考虑这一点。 2/ 你不需要(这是用户错误,不是正常的运行条件)。但是,如果您愿意,(可能在 DEBUG 构建中)然后考虑最后一个元素的
next指针应该是什么样子。实际上,考虑一下你将如何在没有哨兵节点的情况下实现 one-past-the-end 迭代器。 -
这可能会导致您的需求过大,但Writing your own STL Container 应该让您了解您可能需要考虑的一些事情。
-
目前有效吗?如果是,您最好将完整代码发布到 CodeReview。那里的人非常擅长全面审查您的代码以找到可能的改进
-
旁注:你几乎肯定需要一个析构函数来进行清理,如果是这样,the Rules of Three and Five 就会生效。
-
@Tzalumen 学习
标签: c++ data-structures iterator