栈(顺序栈)----C语言

栈是一种运算受限的线性表,是一种先进后出的数据结构,限定只能在一端进行插入和删除操作,允许操作的一端称为栈顶,不允许操作的称为栈底

顺序栈(顺序结构)

顺序栈:用一段连续的存储空间来存储栈中的数据元素,比较常见的是用数组来实现顺序栈

顺序存储结构:1.元素所占的存储空间必须连续(这里的连续是指的逻辑连续,而不是物理连续)

       2.元素在存储空间的位置是按逻辑顺序存放的

 

(图片来源:https://www.cnblogs.com/misterge/p/3427587.html)

顺序栈的实现一般包括如下部分

代码声明部分

 

#include <stdio.h>
#include <stdlib.h>

#define MAX_SIZE 5    /* 栈最大容量 */
#define Empty 0        /* 空 */
#define Full 1        /* 满 */
#define Avail -1    /* 可用 */

typedef struct sta
{
    int *top;            /* 栈顶指针 */
    int *bottom;        /* 栈底指针 */
    int stack_size;        /* 栈的最大容量 */
}stack;
stack Push (stack p);        /* 入栈 */
void DisplyStack (stack p);    /* 遍历栈中元素 */
stack Pop (stack p);        /* 出栈 */
stack InitStack (stack p);    /* 初始化栈 */
int StackEmpty (stack p);    /* 判断栈是否为空 */
int StackFull (stack p);    /* 判断栈是否为满 */

 

一、栈的声明

第一种:

1 typedef struct sta
2 {
3     int stack[SIZE];    /* 存放栈中元素的一维数组 */
4     int top;            /* 存放栈顶元素的下标 */
5 }stack;

(这里只用了一个top来指向栈顶的位置,也可以用两个变量base、top来分别指向栈空间栈底位置和栈顶位置)

 

第二种:(本篇随笔是使用的第二种声明方式)

1 typedef struct sta
2 {
3     int *top;            /* 栈顶指针 */
4     int *bottom;        /* 栈底指针 */
5     int stack_size;        /* 栈的最大容量 */
6 }stack;

 

 二、栈的初始化

 1 /* Function:栈的初始化 */
 2 stack InitStack (stack p)
 3 {
 4     p.bottom = (int *)malloc(p.stack_size * sizeof(int));
 5     if (p.bottom == NULL)
 6     {
 7         printf("初始化栈失败\n");
 8         exit(0);
 9     }
10     p.top = p.bottom;
11     p.stack_size = MAX_SIZE;
12 
13     return p;
14 }

 

三、入栈(压栈)

 

 1 /* Function:入栈 */
 2 stack Push (stack p)
 3 {
 4     int data;
 5     if (StackFull(p) == Full)
 6     {
 7         printf("栈空间已满,无法入栈");
 8         return p;
 9     }
10     printf("Please input data");
11     scanf("%d", &data);
12     *p.top = data;
13     p.top++;
14 
15     return p;
16 }

 

四、出栈

 

 1 /* Function:出栈 */
 2 stack Pop (stack p)
 3 {
 4     if (StackEmpty(p) == Empty)
 5     {
 6         printf("栈为空栈,无法出栈 ");
 7         return p;
 8     }
 9     p.top--;
10     printf("出栈元素为:%d\n", *p.top);
11 
12     return p;
13 }

 (栈顶指针指向的位置是栈顶指针的后一个元素,所以在出栈时需要p.top--,才能指向出栈的元素)

 

五、判断栈是否为空

 1 /* Function:判断栈是否为空 */
 2 int StackEmpty (stack p)
 3 {
 4     if (p.top == p.bottom)
 5     {
 6         return Empty;
 7     }
 8     else
 9     {
10         return Avail;
11     }
12 }

 

六、判断栈是否为满

 1 /* Function:判断栈是否为满 */
 2 int StackFull (stack p)
 3 {
 4     if (p.top - p.bottom == p.stack_size)
 5     {
 6         return Full;
 7     }
 8     else
 9     {
10         return Avail;
11     }
12 }

 

七、遍历栈中的元素

 1 /* Function:遍历栈中元素,从栈顶到栈底*/
 2 void DisplyStack (stack p)
 3 {
 4     if (StackEmpty(p) == Empty)
 5     {
 6         printf("栈为空栈,无法遍历\n");
 7         return;
 8     }
 9     printf("栈中元素为:");
10     printf("顶端[");
11     while (p.top != p.bottom)
12     {
13         p.top--;
14         printf("%d-", *p.top);
15     }
16     printf("]底端\n");
17 }

 

顺序栈实现--完整代码

  1 #include <stdio.h>
  2 #include <stdlib.h>
  3 
  4 #define MAX_SIZE 5    /* 栈最大容量 */
  5 #define Empty 0        /* 空 */
  6 #define Full 1        /* 满 */
  7 #define Avail -1    /* 可用 */
  8 
  9 typedef struct sta
 10 {
 11     int *top;            /* 栈顶指针 */
 12     int *bottom;        /* 栈底指针 */
 13     int stack_size;        /* 栈的最大容量 */
 14 }stack;
 15 stack Push (stack p);        /* 入栈 */
 16 void DisplyStack (stack p);    /* 遍历栈中元素 */
 17 stack Pop (stack p);        /* 出栈 */
 18 stack InitStack (stack p);    /* 初始化栈 */
 19 int StackEmpty (stack p);    /* 判断栈是否为空 */
 20 int StackFull (stack p);    /* 判断栈是否为满 */
 21 
 22 int main()
 23 {
 24     stack p;
 25     char ch;
 26     
 27     p.stack_size = MAX_SIZE;
 28     p = InitStack (p);    /* 初始化栈 */
 29     printf("Do you want to push to stack?(Y/N)");
 30     scanf(" %c", &ch);
 31     while (ch == 'Y' || ch == 'y')
 32     {
 33         p = Push (p);    /* 入栈 */
 34         DisplyStack (p);/* 打印栈中元素 */
 35         printf("Do you want to push to stack?(Y/N)");
 36         scanf(" %c", &ch);
 37     }
 38     printf("Do you want to pop (Y/N)");
 39     scanf(" %c", &ch);
 40     while (ch == 'Y' || ch == 'y')
 41     {
 42         p = Pop (p);
 43         DisplyStack (p);
 44         printf("Do you want to pop (Y/N)");
 45         scanf(" %c", &ch);
 46     }
 47 
 48     return 0;
 49 }
 50 /* Function:判断栈是否为空 */
 51 int StackEmpty (stack p)
 52 {
 53     if (p.top == p.bottom)
 54     {
 55         return Empty;
 56     }
 57     else
 58     {
 59         return Avail;
 60     }
 61 }
 62 /* Function:判断栈是否为满 */
 63 int StackFull (stack p)
 64 {
 65     if (p.top - p.bottom == p.stack_size)
 66     {
 67         return Full;
 68     }
 69     else
 70     {
 71         return Avail;
 72     }
 73 }
 74 /* Function:入栈 */
 75 stack Push (stack p)
 76 {
 77     int data;
 78     if (StackFull(p) == Full)
 79     {
 80         printf("栈空间已满,无法入栈");
 81         return p;
 82     }
 83     printf("Please input data");
 84     scanf("%d", &data);
 85     *p.top = data;
 86     p.top++;
 87 
 88     return p;
 89 }
 90 /* Function:出栈 */
 91 stack Pop (stack p)
 92 {
 93     if (StackEmpty(p) == Empty)
 94     {
 95         printf("栈为空栈,无法出栈 ");
 96         return p;
 97     }
 98     p.top--;
 99     printf("出栈元素为:%d\n", *p.top);
100 
101     return p;
102 }
103 /* Function:栈的初始化 */
104 stack InitStack (stack p)
105 {
106     p.bottom = (int *)malloc(p.stack_size * sizeof(int));
107     if (p.bottom == NULL)
108     {
109         printf("初始化栈失败\n");
110         exit(0);
111     }
112     p.top = p.bottom;
113     p.stack_size = MAX_SIZE;
114 
115     return p;
116 }
117 /* Function:遍历栈中元素,从栈顶到栈底*/
118 void DisplyStack (stack p)
119 {
120     if (StackEmpty(p) == Empty)
121     {
122         printf("栈为空栈,无法遍历\n");
123         return;
124     }
125     printf("栈中元素为:");
126     printf("顶端[");
127     while (p.top != p.bottom)
128     {
129         p.top--;
130         printf("%d-", *p.top);
131     }
132     printf("]底端\n");
133 }

 

栈顶指针的指向有两种方式,一种是指向栈顶元素的后一元素(本文使用的就是这种),另一种是指向栈顶元素,两者在判断栈为空和满的条件、入栈、出栈时栈顶指针的移动有一些差异

 

posted @ 2019-03-02 21:15  Luv3  阅读(23584)  评论(2编辑  收藏  举报