数据结构之队列

队列是一种特殊的线性表,特殊之处在于它只允许在表的前端(front)进行删除操作,而在表的后端(rear)进行插入操作,和栈一样,队列是一种操作受限制的线性表。进行插入操作的端称为队尾,进行删除操作的端称为队头。


队列特性:先进先出(FIFO)——先进队列的元素先出队列。来源于我们生活中的队列(先排队的先办完事)。

队列有下面几个操作:

  • InitQueue()   ——初始化队列
  • EnQueue()        ——进队列
  • DeQueue()        ——出队列
  • IsQueueEmpty()——判断队列是否为空
  • IsQueueFull()    ——判断队列是否已满


//
//  Header.h
//  队列
//
//  Created by mouweng on 17/3/19.
//  Copyright © 2017年 队列. All rights reserved.
//

#ifndef Header_h
#define Header_h
#include<iostream>
using namespace std;


class MyQueue
{
public:
    MyQueue(int QueueCapacity);//创建队列
    virtual ~MyQueue();        //销毁队列
    void ClearQueue();         //清空队列
    bool QueueEmpty() const;   //判空队列
    bool QueueFull() const;    //判断为满
    int QueueLength() const;   //返回队列长度
    bool EnQueue(int element); //新队列入队
    bool DeQueue(int &element);//首元素出队
    void QueueTraverse();      //遍历队列
private:
    int *m_pQueue;             //队列数组指针
    int m_iQueueLength;        //队列元素个数
    int m_iQueueCapacity;      //队列数组容量
    int m_iHead;
    int m_iTail;
};

#endif /* Header_h */



我们所知道,队列可以是直行也可以是环形,之所以把队列设成环形的原因呢,是可以节省内存空间。

下面分别给出两种队列的代码


直行队列源码如下:

//
//  Header.h
//  直行队列
//
//  Created by mouweng on 17/3/20.
//  Copyright © 2017年 直行队列. All rights reserved.
//

#ifndef Header_h
#define Header_h

#include<iostream>
using namespace std;


class MyQueue
{
public:
    MyQueue(int QueueCapacity);//创建队列
    virtual ~MyQueue();        //销毁队列
    void ClearQueue();         //清空队列
    bool QueueEmpty() const;   //判空队列
    bool QueueFull() const;    //判断为满
    int QueueLength() const;   //返回队列长度
    bool EnQueue(int element); //新队列入队
    bool DeQueue(int &element);//首元素出队
    void QueueTraverse();      //遍历队列
private:
    int *m_pQueue;             //队列数组指针
    int m_iQueueLength;        //队列元素个数
    int m_iQueueCapacity;      //队列数组容量
    int m_iHead;
    int m_iTail;
};

#endif /* Header_h */

//
//  main.cpp
//  直行队列
//
//  Created by mouweng on 17/3/20.
//  Copyright © 2017年 直行队列. All rights reserved.
//

#include <iostream>
using namespace std;
#include "Header.h"

MyQueue::MyQueue(int QueueCapacity)
{
    m_iQueueCapacity= QueueCapacity;
    m_iHead=0;
    m_iTail=0;
    m_iQueueLength=0;
    m_pQueue=new int[m_iQueueCapacity];
}
MyQueue::~MyQueue()
{
    delete [] m_pQueue;
    m_pQueue=NULL;
}

void MyQueue::ClearQueue()
{
    m_iHead=0;
    m_iTail=0;
    m_iQueueLength=0;
}



bool MyQueue::QueueEmpty() const
{
    if(m_iQueueLength==0)
        return true;
    else
        return false;
}
bool MyQueue::QueueFull() const
{
    if(m_iQueueLength==m_iQueueCapacity)
        return true;
    else
        return false;
}



int MyQueue::QueueLength() const
{
    return m_iQueueLength;
}


bool MyQueue::EnQueue(int element)
{
    if(QueueFull())
    {
        return false;
    }
    else
    {
        m_pQueue[m_iTail]=element;
        m_iTail++;
        m_iQueueLength++;
        return true;
    }
    
}

bool MyQueue::DeQueue(int &element)
{
    if(QueueEmpty())
    {
        return false;
    }
    else
    {
        element = m_pQueue[m_iHead];
        m_iHead++;
        m_iQueueLength--;
        return true;
    }
}

void MyQueue::QueueTraverse()
{
    cout<<endl;
    for(int i=m_iHead;i<m_iTail;i++)
    {
        cout<<m_pQueue[i]<<endl;
    }
    cout<<endl;
}



int main(int argc, const char * argv[])
{
    MyQueue *p=new MyQueue(10);
    
    p->EnQueue(10);
    p->EnQueue(12);
    p->EnQueue(16);
    p->EnQueue(18);
    p->EnQueue(20);
    p->QueueTraverse();
    
    int e=0;
    p->DeQueue(e);
    cout<<e<<endl;
    
    p->DeQueue(e);
    cout<<e<<endl;
    
    p->EnQueue(21);
    p->EnQueue(22);
    p->QueueTraverse();
    
    cout<<endl;
    p->ClearQueue();
    
    p->QueueTraverse();
    
    p->EnQueue(20);
    p->EnQueue(30);
    p->QueueTraverse();
    
    delete p;
    p=NULL;
    return 0;
}



环形队列源码如下:

//
//  main.cpp
//  环形队列
//
//  Created by Anthony on 17/3/19.
//  Copyright © 2017年 队列. All rights reserved.
//

#include <iostream>
using namespace std;
#include "Header.h"

MyQueue::MyQueue(int QueueCapacity)
{
    m_iQueueCapacity= QueueCapacity;
    m_iHead=0;
    m_iTail=0;
    m_iQueueLength=0;
    m_pQueue=new int[m_iQueueCapacity];
}
MyQueue::~MyQueue()
{
    delete [] m_pQueue;
    m_pQueue=NULL;
}

void MyQueue::ClearQueue()
{
    m_iHead=0;
    m_iTail=0;
    m_iQueueLength=0;
}



bool MyQueue::QueueEmpty() const
{
    if(m_iQueueLength==0)
        return true;
    else
        return false;
}
bool MyQueue::QueueFull() const
{
    if(m_iQueueLength==m_iQueueCapacity)
        return true;
    else
        return false;
}



int MyQueue::QueueLength() const
{
    return m_iQueueLength;
}


bool MyQueue::EnQueue(int element)
{
    if(QueueFull())
    {
        return false;
    }
    else
    {
        m_pQueue[m_iTail]=element;
        m_iTail++;
        m_iTail=m_iTail%m_iQueueCapacity;//因为是一个环形队列
        m_iQueueLength++;
        return true;
    }

}

bool MyQueue::DeQueue(int &element)
{
    if(QueueEmpty())
    {
        return false;
    }
    else
    {
        element = m_pQueue[m_iHead];
        m_iHead++;
        m_iHead=m_iHead%m_iQueueCapacity;//因为是一个环形队列
        m_iQueueLength--;
        return true;
    }
}

void MyQueue::QueueTraverse()
{
    cout<<endl;
    for(int i=m_iHead;i<m_iHead+m_iQueueLength;i++)
    {
        cout<<m_pQueue[i%m_iQueueCapacity]<<endl;
    }
    cout<<endl;
}



int main(int argc, const char * argv[])
{
    MyQueue *p=new MyQueue(4);
    
    p->EnQueue(10);
    p->EnQueue(12);
    p->EnQueue(16);
    p->EnQueue(18);
    p->EnQueue(20);
    p->QueueTraverse();
    
    int e=0;
    p->DeQueue(e);
    cout<<e<<endl;
    
    p->DeQueue(e);
    cout<<e<<endl;
    
    p->EnQueue(20);
    p->EnQueue(22);
    p->QueueTraverse();
    
    cout<<endl;
    p->ClearQueue();
    
    p->QueueTraverse();
    
    p->EnQueue(20);
    p->EnQueue(30);
    
    
    
    
    
    
    delete p;
    p=NULL;
    
    
    
    
    return 0;
}



接下来继续给大家延时更加灵活更加节省空间的队列实现方式,是通过链表来粗存队列的元素,为链表队列。

//
//  Header.h
//  链表队列
//
//  Created by mouweng on 17/3/20.
//  Copyright © 2017年 链表队列. All rights reserved.
//

#ifndef Header_h
#define Header_h
#include<iostream>
using namespace std;


class MyQueue
{
public:
    MyQueue();//创建队列
    virtual ~MyQueue();        //销毁队列
    void ClearQueue();         //清空队列
    bool QueueEmpty() const;   //判空队列
    int QueueLength() const;   //返回队列长度
    bool EnQueue(int element); //新队列入队
    bool DeQueue();//首元素出队
    void QueueTraverse();      //遍历队列
private:
    class Node
    {
    public:
        int data;
        Node *next;
        void PrintData()
        {
            cout<<data<<endl;
        }
    };
    Node *m_pQueue;             //队列数组指针
    int m_iQueueLength;        //队列元素个数
    int m_iHead;
    int m_iTail;
};
#endif /* Header_h */

//
//  main.cpp
//  链表队列
//
//  Created by mouweng on 17/3/20.
//  Copyright © 2017年 链表队列. All rights reserved.
//

#include <iostream>
using namespace std;
#include "Header.h"

MyQueue::MyQueue()
{
    m_iHead=0;
    m_iTail=0;
    m_iQueueLength=0;
    m_pQueue=new Node;
    m_pQueue->data=0;
    m_pQueue->next=NULL;
}

MyQueue::~MyQueue()
{
    ClearQueue();
    delete m_pQueue;
}

void MyQueue::ClearQueue()
{
    m_iHead=0;
    m_iTail=0;
    m_iQueueLength=0;
    Node *currentNode=m_pQueue->next;
    while(currentNode!=NULL)
    {
        Node *temp=currentNode->next;
        delete currentNode;
        currentNode= temp;
    }
    m_pQueue->next=NULL;
}



bool MyQueue::QueueEmpty() const
{
    if(m_iQueueLength==0)
        return true;
    else
        return false;
}


int MyQueue::QueueLength() const
{
    return m_iQueueLength;
}


bool MyQueue::EnQueue(int element)
{
    Node *temp=m_pQueue;
    Node *currentNode= new Node;
    if(currentNode==NULL)
        return false;
    currentNode->data=element;
    while(temp->next!=NULL)
        temp=temp->next;
    currentNode->next=temp->next;
    temp->next=currentNode;
    m_iQueueLength++;
    return true;
}

bool MyQueue::DeQueue()
{
    if(QueueEmpty())
    {
        return false;
    }
    else
    {
        Node *temp=m_pQueue;
        for(int i=0;i<m_iQueueLength-1;i++)
            temp=temp->next;
        Node *aftertemp=temp->next;
        temp->next=aftertemp->next;
        delete aftertemp;
        m_iQueueLength--;
        return true;
    }
}

void MyQueue::QueueTraverse()
{
    cout<<endl;
    Node *temp=m_pQueue;
while(temp->next!=NULL)
{
    temp=temp->next;
    temp->PrintData();
}
    cout<<endl;
}



int main(int argc, const char * argv[])
{
    MyQueue *p=new MyQueue();
    
    p->EnQueue(10);
    p->EnQueue(12);
    p->EnQueue(16);
    p->EnQueue(18);
    p->EnQueue(20);
    p->QueueTraverse();
    p->QueueLength();
    
    p->DeQueue();
    p->DeQueue();
    p->QueueTraverse();
    
    p->EnQueue(21);
    p->EnQueue(22);
    p->QueueTraverse();
    
    cout<<endl;
    p->ClearQueue();
    
    p->QueueTraverse();
    
    p->EnQueue(20);
    p->EnQueue(30);
    p->QueueTraverse();
    
    delete p;
    p=NULL;
    return 0;
}







  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值