重温数据结构(三)

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/sinat_31803737/article/details/52190733

最近几天都都忙的没时间看书了。游戏打包完成,让我继续来看栈和队列吧。

栈是限定仅在表尾进行插入和删除操作的线性表。
队列是只允许在一端进行插入操作、而在另一端进行删除操作的线性表

一.栈

1.栈的几个定义

允许插入和删除的一端为栈顶,另一端为栈底。
空栈:不含任何数据元素的栈。
栈又称为后进先出(Last In Fisrt Out)的线性表。
栈的插入操作,称为进栈,或入栈,压栈。
栈的删除操作,称为出栈。

栈

2.顺序栈

数组下标为0的一端作为栈底,定义一个top变量来指示栈顶元素在数组中的位置。
当栈中有一个元素时,top=0。空栈的判断条件为top=-1。

//栈的定义
typedef int ElemType; //栈中存储元素类型,定义为int
#define MAX_SIZE  100 //数组长度
typedef struct  {
    ElemType data[MAX_SIZE]; //栈内元素数组
    int top; //栈顶指针
}SqStack;

void push (SqStack *stack , ElemType e){
    if(stack->top == MAX_SIZE -1){
        //栈满
    }else{
        stack->top++;//入栈,栈顶 指针+1
        stack->data[stack->top] = e;//赋值
    }
}

void pop (SqStack * stack , ElemType *e){
    if(stack->top == -1){
        //空栈
    }else{
        *e = stack->data[stack->top];
        stack->top--;//出栈,栈顶 指针-1
    }
}

3.双栈

在数组的两端,分别放两个栈的栈顶指针top1,top2,向中间靠拢。
栈1为空是top1=-1,栈2为空是top2=MAX_SIZE-1,栈满是top1=top2-1。
双栈只针对两个具有相同数据类型的栈的一个设计上的技巧。

//双栈定义
typedef struct  {
    ElemType data[MAX_SIZE]; //栈内元素数组
    int top1; //栈顶指针
    int top2;//第二个栈顶指针
}SqDoubleStack;

void push(SqDoubleStack *stack , ElemType e,int stackNum){
    if(stack->top1 == stack->top2 - 1){
        //栈满
    }else if(stackNum == 1){ //栈的标号
        stack->top1++;//入栈,栈顶 指针+1
        stack->data[stack->top1] = e;//赋值
    }else if(stackNum == 2){
        stack->top2--;//入栈,栈顶 指针+1
        stack->data[stack->top2] = e;//赋值
    }
}

void pop(SqDoubleStack * stack , ElemType *e ,int stackNum){
    if(stackNum == 1){ //栈的标号
        if(stack->top1 != -1){//栈1非空
             *e =stack->data[stack->top1];
            stack->top2++;//出栈,栈顶 指针-1
        }
    }else if(stackNum == 2){
        if(stack->top2 != MAX_SIZE){//栈2非空
            *e=stack->data[stack->top2];
            stack->top2++;//出栈,栈顶 指针-1
        }
    }
}

4.链栈
基本不会出现栈满的情况,除非内存已经没有可以使用的空间。
栈顶指针top 为 头指针。
空栈则表示为top = null;

//栈结点定义
typedef struct {
    ElemType data;//数据域
    StackNode *next;//指针域
}StackNode,*LinkStackPtr;
//链栈定义
typedef struct {
    LinkStackPtr top;//栈顶指针
    int count;//栈内元素数量
}LinkStack;

void push(LinkStack *stack , ElemType e){
    LinkStackPtr s = (LinkStackPtr)malloc(sizeof(LinkStackPtr));
    s->data = e;
    //将top指针前移
    s->next = stack->top;
    stack->top = s;
    stack->count++;
}

void pop(LinkStack *stack , ElemType *e){
    if(stack->top != NULL){  //非空栈
        LinkStackPtr s;
        *e = stack->top->data;
        //将top指针后移
        s = stack->top;
        stack->top = s->next;
        free(s);
        stack->count--;
    }
}

对比顺序栈和链栈,时间复杂度都为O(1),对于空间性,顺序栈需要先确定好长度,会造成内存空间的浪费。链栈则要求每个元素都有指针域,增加一些内存的开销,但对于栈的长度无限制。

二.队列

猜你喜欢

转载自blog.csdn.net/sinat_31803737/article/details/52190733