这篇博文里面说的是c++中通过指针来实现队列,本身思想是很简单的,也没有什么太多需要说的,只需要注意一些细节的问题,其实,我想说的是,作为面向对象,我们应该从调用类中存在的方法去思考我们应该定义哪些变量,如果这样思考应该就变得简单了,这里我再画入队和出队的图片,并进行阐述,代码是可以直接运行的,包括一些小的知识点也进行了很好的阐述,
第1张图片是节点的删除,temp首先是头节点,然后我们将头结点赋值给temp,然后将head节点变成之前的头结点之后的那个节点,在删除temp节点就可以,对照代码来看就简单了
第2张图片是节点的添加,这是队列不为空的情况,如果为空的话,直接添加的节点就是头节点就是了,如果不为空,那么我们让rear指向我们需要添加的节点,然后把我们添加的节点编程rear节点就可以了
//这段代码是通过指针的方式来模仿队列,毕竟通过数组来模仿队列的话有太多的缺陷了,
//这里的队列中的每项是通过typedef来定义的,如果我们需要改变对应项,只需要改变typedef的内容就好
//这里我们使用了const来修饰几个函数,使用const修饰函数的意思是,我们在这个函数体里面是不可以修改当前对象里面的内容的,增加了程序的健壮性
#include<iostream>
using namespace std;
typedef int Item;
class Queue{
private :
//队列的每个节点
struct Node{Item item;struct Node *next;};
//这个地方应该是个默认大小 ,这是c++primer里面的写法,我试了很多方法除了这个方法以外好像都不怎么能初始化
enum{Q_size=10};
//指向队列的头结点
Node *front;
//指向队列的尾节点
Node *rear;
//队列中存在的节点的个数
int items;
//动态分配的节点的长度,这种定义的方式只能通过成员列表来初始化
const int qsize;
//私有的构造函数
Queue(const Queue & q):qsize(0){}
//私有赋值运算符
Queue & operator=(const Queue &q){
return *this;
}
public :
//声明构造函数
Queue(int qs=Q_size);
//声明析构函数
~Queue();
//声明判断是否为空的函数
bool isEmpty() const;
//声明判断是否队列已满的函数
bool isFull() const;
//声明返回队列长度的函数
int queueCount() const;
//声明入队函数
bool enqueue(const Item &item);
//声明出队函数
bool dequeue(Item &item);
};
//实现构造函数
Queue::Queue(int qs) : qsize(qs){
//初始化是头节点和尾节点都为空
front=rear=NULL;
//队列中存在的节点个数为0
items=0;
}
Queue::~Queue(){
//声明一个临时节点
Node *temp;
//头节点不为空
while(front!=NULL){
//将头节点给临时节点
temp=front;
//将头结点的下一个节点变成头节点
front=front->next;
//删除临时节点,也就是之前的头节点
delete temp;
}
}
//实现队列是否为空
bool Queue::isEmpty() const{
return items==0;
}
//实现队列是否已经满
bool Queue::isFull() const{
return items==qsize;
}
//返回队列中的节点的个数
int Queue::queueCount() const{
return items;
}
//入队
bool Queue::enqueue(const Item & item){
//如果队列已满,则添加失败,返回为false
if(isFull()){
return false;
}
//申请一个节点
Node * add=new Node;
add->item=item;
add->next=NULL;
//将队列中的节点的个数加1
items++;
//如果为空队列的话,那么添加的节点就是头节点
if(front==NULL)
front=add;
//如果不是尾节点的话,那么就需要在队列的节点的尾节点后加入节点
else rear->next=add;
//将添加的节点变为尾节点
rear=add;
return true;
}
//出队
bool Queue::dequeue(Item & item){
//如果队列为空,则出队失败
if(front==NULL){
return false;
}
//因为传递的是引用,所以可以直接改变
item=front->item;
//节点的个数减1
items--;
//和析构函数删除节点的方式相同
Node *temp=front;
front=front->next;
delete temp;
//如果节点个数为0的话,说明头和尾都为空
if(items==0)
front=rear=NULL;
return true;
}
int main(){
Queue queue(100);
Item temp;
for(int i=0;i<100;i++){
temp=i;
if(queue.enqueue(temp))
return -1;
}
for(int t=0;t<100;t++){
if(queue.dequeue(temp))
return -1;
cout<<temp<<endl;
}
system("pause");
return 0;
}