栈和向量、列表一样,是线性序列 的一种
但它的核心特点在于:只能访问和操作序列的一端(栈顶) 并且是 LIFO (Last In First Out)
可以用一叠盘子来进行比喻,对于一叠盘子,我们对它进行操作的时候,要么是拿走顶上的一块盘子,要么就是在顶上放一块盘子。
所以对应的,栈有最为基本的两个操作,push(入栈)和pop(出栈)
以下就用C语言来实现一个数据类型为int的简单的栈结构
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
#include<stdio.h>
#include<stdlib.h>
typedef struct Node{ // 栈节点 其实实现的是链表的一个节点
int data ; //数据域
struct Node* next; // 下一个节点的指针
}Node;
typedef struct Stack{ //栈结构
int size ; // 栈的大小
Node* top ;
Node* bottom ;
}Stack;
void init(Stack* ps){ //初始化栈函数
ps->size = 0 ; // 这里 ps是一个栈指针 结构体指针->成员 是 结构体->成员 的一种简便写法
Node* node = malloc(sizeof(Node));
ps->bottom = ps->top = node ; //初始化一个空指针作为栈底
ps->top->next = NULL;
}
void push(Stack* ps,int data){ // 入栈函数
ps->size ++ ; // 栈长度加 1
Node* newNode = malloc(sizeof(Node)); //为新节点申请内存空间
newNode->data = data ; // 为新节点赋值
newNode->next = ps->top ; // 注意接下来两步的顺序 先将new->next设为ps->top 再将newNode作为栈顶
ps->top = newNode;
}
void pop(Stack* ps){
if(ps->size < 1){
printf("Empty Stack!");//空栈无法出栈
return ;
}
ps->size -- ; // 栈长度减一
Node* temp = ps->top ; //temp指针用来进行内存释放操作 避免内存泄露
ps->top = ps->top->next ; // 将栈顶的下一个节点作为栈顶
free(temp); //释放栈顶内存空间
temp = NULL ; // 安全操作
}
void tranverse(Stack* ps){ //遍历栈结构 并输出数据
int i ;
if(ps->size < 1){
printf("Empty Stack!");//空栈无法遍历
return ;
}
while( ps->size > 0){
printf("%d\n",ps->top->data);
pop(ps);
}
}
int main(){
Stack stack ;
init(&stack);
push(&stack,1);
push(&stack,5);
push(&stack,2);
printf("size :%d\n",ps->size);
pop(&stack);
printf("size :%d\n",ps->size);
tranverse(&stack);
}
输出结果
size :3
size :2
5
1