循环双向链表复制构造函数 C++
Circular Doubly Linked List Copy Constructor C++
我正在尝试将复制构造函数实现到我的循环双向链表中,但我无法使其工作。文件确实复制了,但顺序不正确。 (注意:plate
定义为 template<typename T>
,我会尽量只包括相关功能)
Class:
plate class CircularDoubleDirectedList : public ICircularDoubleDirectedList<T> {
private:
plate class Node {
public:
T data;
Node *next;
Node *prev;
};
Node<T> *current;
int nrOfElements;
direction currentDirection;
public:
CircularDoubleDirectedList() { nrOfElements = 0; currentDirection = FORWARD; current = nullptr; }
virtual ~CircularDoubleDirectedList();
CircularDoubleDirectedList(const CircularDoubleDirectedList<T>& origObj);
CircularDoubleDirectedList& operator=(const CircularDoubleDirectedList<T>& origObj);
void addAtCurrent(const T& element);
T getElementAtCurrent() const;
void removeAtCurrent();
int size() const;
void changeDirection();
void moveCurrent();
direction getCurrentDirection() const;
};
我对复制构造函数的尝试:
plate CircularDoubleDirectedList<T>::CircularDoubleDirectedList(const CircularDoubleDirectedList<T>& origObj) {
current = nullptr;
nrOfElements = 0;
Node<T> *tmp = origObj.current;
currentDirection = origObj.currentDirection;
while (nrOfElements < origObj.nrOfElements) {
addAtCurrent(tmp->data);
tmp = tmp->next;
}
}
加法器:
plate void CircularDoubleDirectedList<T>::addAtCurrent(const T& element) {
Node<T> *tmp = new Node<T>;
tmp->data = element;
tmp->next = nullptr;
tmp->prev = nullptr;
if (current == nullptr) {
tmp->next = tmp;
tmp->prev = tmp;
}
else if (nrOfElements == 1) {
tmp->next = current;
tmp->prev = current;
current->next = tmp;
current->prev = tmp;
}
else {
if (currentDirection == FORWARD) {
tmp->prev = current;
tmp->next = current->next;
current->next->prev = tmp;
current->next = tmp;
}
else if (currentDirection == BACKWARD) {
tmp->prev = current->prev;
tmp->next = current;
current->prev->next = tmp->prev;
current->prev = tmp;
}
}
nrOfElements += 1;
current = tmp;
}
谢谢。
正如我在评论中指出的那样,问题似乎出在最后一个函数中。所以我尝试以一种更具可读性的方式从头开始编写它:
plate void CircularDoubleDirectedList<T>::addAtCurrent(const T& element) {
Node<T> *tmp = new Node<T>;
tmp->data = element;
if (current == nullptr) {
tmp->next = tmp;
tmp->prev = tmp;
} else {
Node<T> * before, after;
if (currentDirection == FORWARD) {
before = current;
after = current->next;
} else { // BACKWARD
before = current->prev;
after = current;
}
before->next = tmp;
tmp->prev = before;
after->prev = tmp;
tmp->next = after;
}
nrOfElements += 1;
current = tmp;
}
我在复制构造函数中看到另一个问题:如果 currentDirection 是向后的,您正在从左到右读取元素,但以 "afterward" 的方式添加元素,结果顺序丢失。
有两种解决方法:可以在扫描时尊重顺序,或者将currentDirection设置为FORWARD,然后设置为正确的值。
plate CircularDoubleDirectedList<T>::CircularDoubleDirectedList(const CircularDoubleDirectedList<T>& origObj) {
current = nullptr;
nrOfElements = 0;
currentDirection = FORWARD; // set the scan direction temporarily
for (Node<T> *tmp = origObj.current; nrOfElements < origObj.nrOfElements; tmp = tmp->next) {
addAtCurrent(tmp->data);
}
if (nrOfElements > 0)
current = current->next; // align with the current of the copyed list
currentDirection = origObj.currentDirection; // set the right direction
}
如果解决了您的问题,请告诉我。
我正在尝试将复制构造函数实现到我的循环双向链表中,但我无法使其工作。文件确实复制了,但顺序不正确。 (注意:plate
定义为 template<typename T>
,我会尽量只包括相关功能)
Class:
plate class CircularDoubleDirectedList : public ICircularDoubleDirectedList<T> {
private:
plate class Node {
public:
T data;
Node *next;
Node *prev;
};
Node<T> *current;
int nrOfElements;
direction currentDirection;
public:
CircularDoubleDirectedList() { nrOfElements = 0; currentDirection = FORWARD; current = nullptr; }
virtual ~CircularDoubleDirectedList();
CircularDoubleDirectedList(const CircularDoubleDirectedList<T>& origObj);
CircularDoubleDirectedList& operator=(const CircularDoubleDirectedList<T>& origObj);
void addAtCurrent(const T& element);
T getElementAtCurrent() const;
void removeAtCurrent();
int size() const;
void changeDirection();
void moveCurrent();
direction getCurrentDirection() const;
};
我对复制构造函数的尝试:
plate CircularDoubleDirectedList<T>::CircularDoubleDirectedList(const CircularDoubleDirectedList<T>& origObj) {
current = nullptr;
nrOfElements = 0;
Node<T> *tmp = origObj.current;
currentDirection = origObj.currentDirection;
while (nrOfElements < origObj.nrOfElements) {
addAtCurrent(tmp->data);
tmp = tmp->next;
}
}
加法器:
plate void CircularDoubleDirectedList<T>::addAtCurrent(const T& element) {
Node<T> *tmp = new Node<T>;
tmp->data = element;
tmp->next = nullptr;
tmp->prev = nullptr;
if (current == nullptr) {
tmp->next = tmp;
tmp->prev = tmp;
}
else if (nrOfElements == 1) {
tmp->next = current;
tmp->prev = current;
current->next = tmp;
current->prev = tmp;
}
else {
if (currentDirection == FORWARD) {
tmp->prev = current;
tmp->next = current->next;
current->next->prev = tmp;
current->next = tmp;
}
else if (currentDirection == BACKWARD) {
tmp->prev = current->prev;
tmp->next = current;
current->prev->next = tmp->prev;
current->prev = tmp;
}
}
nrOfElements += 1;
current = tmp;
}
谢谢。
正如我在评论中指出的那样,问题似乎出在最后一个函数中。所以我尝试以一种更具可读性的方式从头开始编写它:
plate void CircularDoubleDirectedList<T>::addAtCurrent(const T& element) {
Node<T> *tmp = new Node<T>;
tmp->data = element;
if (current == nullptr) {
tmp->next = tmp;
tmp->prev = tmp;
} else {
Node<T> * before, after;
if (currentDirection == FORWARD) {
before = current;
after = current->next;
} else { // BACKWARD
before = current->prev;
after = current;
}
before->next = tmp;
tmp->prev = before;
after->prev = tmp;
tmp->next = after;
}
nrOfElements += 1;
current = tmp;
}
我在复制构造函数中看到另一个问题:如果 currentDirection 是向后的,您正在从左到右读取元素,但以 "afterward" 的方式添加元素,结果顺序丢失。 有两种解决方法:可以在扫描时尊重顺序,或者将currentDirection设置为FORWARD,然后设置为正确的值。
plate CircularDoubleDirectedList<T>::CircularDoubleDirectedList(const CircularDoubleDirectedList<T>& origObj) {
current = nullptr;
nrOfElements = 0;
currentDirection = FORWARD; // set the scan direction temporarily
for (Node<T> *tmp = origObj.current; nrOfElements < origObj.nrOfElements; tmp = tmp->next) {
addAtCurrent(tmp->data);
}
if (nrOfElements > 0)
current = current->next; // align with the current of the copyed list
currentDirection = origObj.currentDirection; // set the right direction
}
如果解决了您的问题,请告诉我。