取消排队不适用于从双链表继承的队列类
dequeue not working for Queue class inherited from a double linked list
我写了一个双链表类,它有insertAtStart, insertAtEnd, removeFromStart, removeFromEnd
个成员函数。检查下面的代码
class Node {
public:
int val;
Node *next;
Node *prev;
Node(int v)
: val(v),
next(nullptr),
prev(nullptr) {}
};
#include<iostream>
using namespace std;
#include "../node.h"
class LinkedList {
private:
Node* start;
Node* end;
public:
LinkedList(): start(nullptr), end(nullptr) { }
void insertAtStart(int val) {
Node* n = new Node(val);
if(start == nullptr) {
start = n;
end = n;
} else {
n->next = start;
start = n;
}
}
void insertAtEnd(int val) {
Node* n = new Node(val);
if(end == nullptr) {
end = n;
start = n;
} else {
end->next = n;
n->prev = end;
end = n;
}
}
void removeFromStart() {
if(start == nullptr) return;
if(start == end) {
start = end = nullptr;
return;
}
start = start->next;
start->prev = nullptr;
}
void removeFromEnd() {
if(end == nullptr) return;
if(start == end) {
start = end = nullptr;
return;
}
end = end->prev;
end->next = nullptr;
}
void printList() {
Node *ptr = start;
while(ptr != nullptr) {
cout << ptr->val << " ";
ptr = ptr->next;
}
cout << endl;
}
};
我使用以下主要函数测试了上面的代码,它运行良好
#include "double-linked-list.h"
int main() {
LinkedList l = LinkedList();
l.insertAtStart(1);
l.insertAtStart(2);
l.insertAtStart(3);
l.insertAtStart(4);
l.insertAtStart(5);
l.insertAtEnd(6);
l.insertAtEnd(7);
l.insertAtEnd(8);
l.insertAtEnd(9);
l.insertAtEnd(10);
l.printList();
l.removeFromStart();
l.printList();
l.removeFromStart();
l.printList();
l.removeFromEnd();
l.printList();
l.removeFromEnd();
l.printList();
return 0;
}
输出:
Inserting 1 at start
Linked list: 1
Inserting 2 at start
Linked list: 2 1
Inserting 3 at start
Linked list: 3 2 1
Inserting 4 at start
Linked list: 4 3 2 1
Inserting 5 at start
Linked list: 5 4 3 2 1
Inserting 6 at end
Linked list: 5 4 3 2 1 6
Inserting 7 at end
Linked list: 5 4 3 2 1 6 7
Inserting 8 at end
Linked list: 5 4 3 2 1 6 7 8
Inserting 9 at end
Linked list: 5 4 3 2 1 6 7 8 9
Inserting 10 at end
Linked list: 5 4 3 2 1 6 7 8 9 10
Removing from start
Linked list: 4 3 2 1 6 7 8 9 10
Removing from start
Linked list: 3 2 1 6 7 8 9 10
Removing from end
Linked list: 3 2 1 6 7 8 9
Removing from end
Linked list: 3 2 1 6 7 8
我现在,写了一个从上面的链表类派生的队列类
#include "../double-linked-list/double-linked-list.h"
class Queue {
private:
LinkedList q;
public:
Queue() {}
void enqueue(int val) {
q.insertAtStart(val);
}
void dequeue() {
q.removeFromEnd();
}
void printQueue() {
q.printList();
}
};
和以下主要功能来测试它
#include "queue.h"
int main() {
Queue q = Queue();
q.enqueue(1);
q.printQueue();
q.enqueue(2);
q.printQueue();
q.enqueue(3);
q.printQueue();
q.enqueue(4);
q.printQueue();
q.enqueue(5);
q.printQueue();
q.dequeue();
q.printQueue();
q.dequeue();
q.printQueue();
}
排队似乎工作得很好,但取消排队却没有。取消排队后它甚至没有打印任何东西。
输出:
Enqueuing 1
1
Enqueuing 2
2 1
Enqueuing 3
3 2 1
Enqueuing 4
4 3 2 1
Enqueuing 5
5 4 3 2 1
Denqueuing
为了尝试调试,我在LinkedList
removeFromEnd
函数中放置了一个cout
语句。
void LinkedList::removeFromEnd(){
if(end == nullptr) return;
if(start == end) {
start = end = nullptr;
return;
}
end = end->prev;
cout << "print statement 1";
end->next = nullptr;
cout << "print statement 2";
}
现在,当我再次运行队列的主函数时,print 语句 1 正在控制台中打印,但第二个语句没有。我不明白为什么。有人可以帮我弄清楚我做错了什么吗?
编辑:
阅读评论后,我对以下功能进行了更改
void insertAtStart(int val) {
Node* n = new Node(val);
// If start and end are null
if(start == nullptr && end == nullptr) {
start = end = n;
}
// There is at least 1 node in the list
else {
n->next = start;
start->prev = n;
// There is only one node in the list
if(start->next == nullptr) {
end->prev = n;
}
start = n;
}
}
void insertAtEnd(int val) {
Node* n = new Node(val);
// If start and end are null
if(start == nullptr && end == nullptr) {
start = end = n;
}
// There is at least 1 node in the list
else {
n->prev = end;
end->next = n;
// There is only one node in the list
if(end->prev == nullptr) {
start->next = n;
}
end = n;
}
}
这奏效了。如果有兴趣,我发布了整个链表类作为答案。
对于初学者来说,程序有内存泄漏,因为您没有删除分配的节点。
至于你的问题,那么这个函数
void insertAtStart(int val) {
Node* n = new Node(val);
if(start == nullptr) {
start = n;
end = n;
} else {
n->next = start;
start = n;
}
}
无效。当新节点添加到列表的开头时,它不会刷新数据成员end->prev
(更准确地说是start->prev
(。也就是说end->prev
总是等于nullptr
。
重写函数至少像
void insertAtStart(int val) {
Node* n = new Node(val);
if(start == nullptr) {
start = n;
end = n;
} else {
n->next = start;
start->prev = n; // <===
start = n;
}
}
在阅读了来自莫斯科的 Vlad 的评论和回答后,我对我的双链表类进行了以下更改,它奏效了。
#include<iostream>
#include "../node.h"
class LinkedList {
private:
Node* start;
Node* end;
public:
LinkedList(): start(nullptr), end(nullptr) { }
void insertAtStart(int val) {
Node* n = new Node(val);
// If the list is empty
if(start == nullptr && end == nullptr) {
start = end = n;
}
// There is at least 1 node in the list
else {
n->next = start;
start->prev = n;
// There is only one node in the list
if(start->next == nullptr) {
end->prev = n;
}
start = n;
}
}
void insertAtEnd(int val) {
Node* n = new Node(val);
// If the list is empty
if(start == nullptr && end == nullptr) {
start = end = n;
}
// There is at least 1 node in the list
else {
n->prev = end;
end->next = n;
// There is only one node in the list
if(end->prev == nullptr) {
start->next = n;
}
end = n;
}
}
void removeFromStart() {
if(start == nullptr) return;
if(start->next == nullptr) {
start = end = nullptr;
return;
}
start = start->next;
start->prev = nullptr;
}
void removeFromEnd() {
if(end == nullptr) return;
if(end->prev == nullptr) {
start = end = nullptr;
return;
}
end = end->prev;
end->next = nullptr;
}
void printList() {
Node *ptr = start;
while(ptr != nullptr) {
std::cout << ptr->val << " ";
ptr = ptr->next;
}
std::cout << std::endl;
}
};
相关文章:
- 继承函数的重载解析
- boost::进程间消息队列引发错误
- 如果我只是不访问queue_front节点的子节点,而是将它们推到队列中呢?还是BFS吗
- 继承期间显示未知行为的子类
- Android NDK传感器向事件队列报告奇怪的间隔
- 头文件-继承c++
- C++优先级队列,按对象的唯一指针的特定方法升序排列
- 为什么在保护模式下继承升级不起作用
- 按对象的特定方法按升序排列的C++优先级队列
- 使用2个键的cpp-stl::优先级队列排序不正确
- 通过继承类使用来自不同命名空间的运算符
- 子目录是否继承属性,例如add_definitions,include_directories和父Cmakelist.t
- 混合组合和继承的C++问题
- 继承:构造函数,初始化C++11中基类的类C数组成员
- 从类继承时,继承的类是否会通过父类重新定义继承的变量
- 公共与私人继承
- 如何创建从同一类继承的不同对象的向量
- 取消排队不适用于从双链表继承的队列类
- 从队列C++继承
- 从模板堆继承的模板优先级队列