1、基础知识
在stack(栈)中,,删除的总是最近插入的元素,也就是先进后出,后进先出的策略;在stack中的插入或添加操作,称为push,出栈的操作称为pop,也称为弹出,即从stack中删除这个元素;stack开始的地方称为栈底,stack结束的地方称为栈顶;入栈出栈皆在栈顶操作,当栈顶等于栈底,元素全部被弹出,称为空栈;如果用数组的方式实现栈,如stack[n]那么,当对一个空栈进行pop操作时称为下溢,pop操作超过n时称为上溢;
2、栈的实现
2.1 栈的链表实现
#include <stdio.h>
#include <stdlib.h>
struct node *stack = NULL;
struct node *stack_top = NULL;
struct node
{
int element;
struct node* pnext;
};
int is_stack_empty(void)
{
return stack->pnext == NULL;
}
struct node *creat_new_stack(void)
{
stack = (struct node *)calloc(0, sizeof(struct node));
if (stack == NULL)
{
printf("malloc new node failed!\n");
return NULL;
}
stack->pnext = NULL;
return stack;
}
int push_stack(int element)
{
struct node *new = NULL;
new = (struct node *)calloc(0, sizeof(struct node));
if (new == NULL)
{
printf("get new stack failed!\n");
return -1;
}
stack_top->pnext = new;
printf("push stack %d success\n", element);
new->pnext = NULL;
stack_top = new;
new->element = element;
return 0;
}
struct node *find_previous(struct node *node)
{
struct node *ptmp = stack;
while (ptmp->pnext != node)
{
ptmp = ptmp->pnext;
}
return ptmp;
}
void pop_stack(void)
{
int ret;
struct node *free_top;
if (is_stack_empty())
{
printf("stack is empty! %p\n", stack->pnext);
return;
}
ret = stack_top->element;
free_top = stack_top;
stack_top = find_previous(stack_top);
stack_top->pnext = NULL;
free(free_top);
printf("pop stack %d success\n", ret);
}
int main(void)
{
struct node *head_stack = NULL;
int i;
head_stack = creat_new_stack();
if (head_stack == NULL)
{
printf("get new stack failed!\n");
return -1;
}
stack_top = head_stack;
for (i = 0; i < 50; i++)
{
push_stack(i + 1);
}
for (i = 0; i < 10; i++)
{
pop_stack();
}
return 0;
}
在很多情况下,栈的使用较为频繁,那么也就意味着malloc与free的操作非常频繁,而对内存的操作开销较大,影响系统的性能,所以在大多数情况下应避免这种频繁的操作;栈的实现也可以通过数组的方式实现,但是数组的大小就是需要值得考虑的问题,但是一般都会有足够的空间,除非对内存空间要求较高才会使用链表的方式;
2.2 栈的数组实现也相对较简单,此处不再讨论