2

我有一个保存数据的链表和一个指向下一个节点的指针Node<T>* next,如下所示:

template <class T>
struct Node
{
    T data;
    Node<T>* next;
};

问题是我想在其中放入一个后增量运算符,因此它返回我节点的先前值,但增加引用。所以如果我这样做

Node<int>* someNode = someList.SomeNode();
Node<int>* tmp = someNode++; 

tmp将是原始someNode值,但someNode会是someNode->next.

是否可以在结构中放置运算符?我已经尝试过,并搜索了如何做到这一点,但由于我不与运营商打交道,所以我不知道该怎么做。

4

4 回答 4

6

您不能将成员函数添加到指针等基本类型。

您要定义的是迭代器。在节点指针上使用包装类来成功:

template <class T>
struct NodeIterator
{
  NodeIterator(Node<T>* current) : current(current) {}
  NodeIterator& operator ++() { current = current->next; return *this; }
  NodeIterator operator ++(int) { 
      NodeIterator retVal = *this; 
      ++(*this);
      return retVal;
  }
  T* operator-> () const { return &current->data; }   
  T& operator * () const { return current->data; }   
  Node<T>* current;
};

请参阅std::slist<> 实现以获取参考。看template<typename _Tp> struct _List_iterator。阅读 STL 实现胜过许多书籍。

用法:

NodeIterator<T> it =  &node;
++it;
T& t = *it;
于 2012-09-17T18:21:21.503 回答
4
Node<T>& operator++(int) {…}

是您要实现的成员。

于 2012-09-17T17:45:54.337 回答
0

为了使您的代码正常工作,您需要能够operator++为您的指针类进行定义。但是,这是不允许的。不过,欢迎您定义其他一些命名函数。例如:

template <typename Node>
Node goto_next(Node& node) {
  Node result = node;
  node = node->next;
  return result;
}

然后你可以像这样使用它:

Node<int>* tmp = goto_next(someNode);

另一种选择是提供一个真正的迭代器类,而不是仅仅使用一个指针:

Node<int>::iterator someNode = someList.begin();
Node<int>::iterator tmp = someNode++;

使您的迭代器保留一个Node<T>*成员,并使++操作员在返回迭代器对象的副本之前更新该内部指针。

于 2012-09-17T18:21:43.673 回答
0

你真的不想那样做。在指针上使用的想法++与常见的迭代器模式非常接近。您应该全力以赴并创建一个真正的迭代器类。想想std::list<T>::iterator

迭代器是非常轻量级的包装器,它为节点指针提供了一个合理的接口,它提供了诸如operator ++移动到下一个节点之类的东西,并重载operator ->以提供对节点数据的简单访问。将客户端代码从使用指针转换为使用迭代器非常简单,因为语法几乎相同。

于 2012-09-17T18:22:13.007 回答