您的位置:首页 > 产品设计 > UI/UE

Stack and Queue

2017-10-31 16:41 375 查看
1、栈的定义

    栈是一种只能在一端进行插入或删除操作的线性表。其中允许进行插入或删除的一端称为栈顶(TOP),表的另一端称为栈底,栈底是固定不变的。

2、栈的特点

    先进后出(FILO)

3、栈的存储结构

    顺序栈和链式栈;栈本质上是线性表

4、栈的数学性质

    当n个元素以某种顺序进栈,并且可在任意时刻出栈(在满足先进后出的前提下)时,所获得的元素排列的数目N恰好满足函数Catalan()的计算。

5、队列的定义

    队列是一种操作受限的线性表,其限制为仅允许在表的一端进行插入,在表的另一端进行删除。可进行插入的一端称为队尾(Rear),可进行删除的一端称为队头(Front)。

6、队列的特点

    先进先出(FIFO)

7、队列的存储结构
    顺序队列和链式队列

8、栈和队列的存储结构

#define maxSize 100 //这里定义一个整型常量maxSize,值为100

//顺序栈定义
typedef struct{
int data[maxSize]; //存放栈中元素
int top; //栈顶指针
}SqStack; //顺序栈类型定义

//链式栈结点定义
typedef struct{
int data; //数据域
struct LNode *next; //指针域
}LNode; //链栈结点定义

//顺序队列定义
typedef struct{
int data[maxSize];
int front; //对头指针
int rear; //队尾指针
}SqQueue; //顺序队列类型定义

//链队定义
//队结点类型定义
typedef struct QNode{
int data; //数据域
struct QNode *next; //指针域
}QNode; //队结点类型定义
//链队类型定义
typedef struct{
QNode *front; //队头指针
QNode *rear; //队尾指针
}LiQueue; //链队类型定义

9、顺序栈
//初始化栈
void initStack(SqStack &st)
{
st.top = -1; //只需将栈顶指针设置为-1
}

//判断栈空
//栈st为空的时候返回1,否则返回0,其对应代码如下:
int isEmpty(SqStack st)
{
if (st.top == -1)
{
return 1;
}
else
{
return 0;
}
}

//进栈
int push(SqStack &st, int x)
{
if (st.top == maxSize-1) //栈满不能进栈,防止上溢
{
return 0;
}
++(st.top); //先移动指针,再进栈
st.data[st.top] = x;
return 1;
}

//出栈
int pop(SqStack &st, int &x)
{
if (st.top == -1) //如果栈空,则不能出栈
{
return 0;
}
x = st.data[st.top];
--(st.top);
return 1;
}

//【简略版】
//定义一个栈并且初始化
int stack[maxSize];
int top = -1;

//元素x进栈
stack[++top] = x;

//元素x出栈
x = stack[top--];

10、链栈
//链栈的初始化
void initStack(LNode *&lst)
{
lst = (LNode*)malloc(sizeof(LNode)); //制造一个头结点
lst->next = NULL;
}

//判断栈空
//当栈空的时候返回1,否则返回0,其代码如下:
init isEmpty(LNode *lst)
{
if (lst->next == NULL)
{
return 0;
}
else
{
return 1;
}
}

//进栈
void push(LNode *lst, int x)
{
LNode *p;
p = (LNode*)malloc(sizeof(LNode)); //为进栈元素申请结点空间
p->next = NULL;
//链表的头插法
p->data = x;
p->next = lst->next;
lst->next = p;
}

//出栈
//在栈不空的情况可以执行,返回1,否则返回0,其实现如下:
int pop(LNode *lst, int &x)
{
LNode *p;
if (lst->next == NULL) //栈空则不能在出栈,返回0
{
return 0;
}
//单链表的删除操作
p = lst->next;
x = p->data;
lst->next = p->next;
free(p);
return 1;
}

11、顺序队
//初始化队列算法
void initQueue(SqQueue &qu)
{
qu.front = qu.rear = 0; //队首和队尾指针重合,并且指向0
}

//判断队空
int isQueueEmpty(SqQueue qu)
{
if (qu.front == qu.rear) //无论队首、队尾指针指向数组中的哪个位置,只要两者重合,即为队空
{
return 1;
}
else
{
return 0;
}
}

//进队
int enQueue(SqQueue &qu, int x)
{
if ((qu.rear+1)%maxSize == qu.front) //队满的判断条件,队满就不能入队
{
return 0;
}
qu.rear = (qu.rear+1)%maxSize; //若队未满,则先移动指针,再存入元素
qu.data[qu.rear] = x;
return 1;
}

//出队
int deQueue(SqQueue &qu, int &x)
{
if (qu.front == qu.rear) //若队空,则不能出队
{
return 0;
}
qu.front = (qu.front+1)%maxSize; //若队不空,则先移动指针,再取出元素
x = qu.data[qu.front];
return 1;
}

12、链队
//初始化链队
void initQueue(LiQueue *&lqu)
{
lqu = (LiQueue*)malloc(sizeof(LiQueue));
lqu->front = lqu->rear = NULL;
}

//判断队空
int isQueueEmpty(LiQueue *lqu)
{
if (lqu->rear==NULL || lqu->front==NULL) //队空判断条件
{
return 1;
}
else
{
return 0;
}
}

//入队
void enQueue(LiQueue *lqu,int x)
{
QNode *p;
p = (QNode*)malloc(sizeof(QNode));
p->data = x;
p->next = NULL;
if (lqu->rear == NULL) //若队列为空,则新结点是队首结点,也是队尾结点
{
lqu->front = lqu->rear = p; //特殊情况,只有一个新结点时,应将front和rear同时指向新结点
}
else
{
lqu->rear->next = p; //将新结点链接到队尾,rear指向空
lqu->rear = p;
}
}

//出队
int deQueue(LiQueue *lqu, int &x)
{
QNode *p;
if (lqu->rear == NULL) //队空不能出队
{
return 0;
}
else //若队中不为空,则从队头取出一个结点
{
p = lqu->front;
}
if (lqu->front == lqu->rear) //队列中只有一个结点时的出队操作需特殊处理
{
lqu->front = lqu->rear = NULL;
}
else
{
lqu->front = lqu->front->next;
}
x = p->data;
free(p);
return 1;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: