首页 > 代码库 > 栈的基本运算实现

栈的基本运算实现

栈(stack)是一种只能在一端进行插入和删除操作的线性表。表中允许进行插入和删除操作的一端称为栈顶。栈顶的当前位置是动态的,由一个称为栈顶指针的位置指示器指示。表的另一端称为栈底。不含数据元素的栈称为空栈。栈的插入操作称为压栈或进栈,栈的删除操作称为退栈或出栈。栈的主要特点是“后进先出(last in first out,LIFO)”。

1、 顺序栈

假定栈的元素个数不超过MaxSize,所有的元素都具有同一数据类型ElemType。采用栈指针s建立和使用顺序栈。在由s指向的顺序栈中,栈空的条件是s->top=-1;栈满的条件是s->top=MaxSize-1;元素e进栈操作是先将栈顶指针加1,然后将元素e放入栈顶指针处;出栈操作是先将栈顶指针处的元素取出,然后将栈顶指针减1。

顺序栈的基本运算实现代码如下:

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

#define MaxSize 50
typedef int ElemType;

typedef struct
{
	ElemType data[MaxSize];
	int top;	//栈顶指针
}SqStack;	//顺序栈

void InitStack(SqStack *&s)	//初始化顺序栈
{
	s=(SqStack *)malloc(sizeof(SqStack));
	s->top=-1;
}

void DestoryStack(SqStack *&s) //销毁顺序栈
{
	free(s);
}

bool StackEmpty(SqStack *s) //判断是否为空栈
{
	return (s->top==-1);
}

bool Push(SqStack *&s, ElemType e)	//压栈
{
	if(s->top==MaxSize-1)	//栈满,栈上溢出
		return false;
	s->top++;
	s->data[s->top]=e;
	return true;
}

bool Pop(SqStack *&s, ElemType &e)	//出栈,注意要使用&e
{
	if(-1==s->top)	//栈空,栈下溢出
		return false;
	e=s->data[s->top];
	s->top--;
	return true;
}

bool GetTop(SqStack *s, ElemType &e)
{
	if(-1==s->top)
		return false;
	e=s->data[s->top];
	return true;
}
int main()
{
	...;
	return 0;
}

2、 链栈

采用链式存储的栈称为链栈,本文采用单链表实现。链栈的优点是不存在栈满上溢的情况。规定栈的所有操作都在单链表的表头进行,头结点为*s,第一个数据结点是栈顶结点,最后一个结点是栈底结点。

在以*s为头结点的链栈中,栈空的条件是s->next==NULL;由于只有在内存溢出时才会出现栈满,而通常不考虑内存溢出的情况,所以在链栈中可以认为不存在栈满的情况;结点*p进栈的操作是在头结点*s之后插入*p结点;出栈的操作是取出头结点之后的结点的data值并剔除该结点。

链栈的基本运算实现代码如下:

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

typedef int ElemType;
typedef struct linknode
{
	ElemType data;
	struct linknode *next;
}LiStack;

void InitStack(LiStack *&s)	//初始化栈
{
	s=(LiStack *)malloc(sizeof(LiStack));
	s->next=NULL;
}

void DestoryStack(LiStack *&s)	//销毁栈
{
	LiStack *p=s,*q=s->next;
	while(q!=NULL)
	{	
		free(p);
		p=q;
		q=q->next;	
	}
	free(p);
}

bool StackEmpty(LiStack *s)	//判断是否空栈
{
	return (s->next==NULL);
}

void Push(LiStack *&s, ElemType e)	//压栈(头插法)
{
	LiStack *p;
	p=(LiStack *)malloc(sizeof(LiStack));
	p->data=http://www.mamicode.com/e;>

几个注意点

1、 函数的形参采用指针+引用的格式,可以改变实参的值;

2、 代码在VC6.0下实现,后缀名使用.cpp可以排除一些错误,如false和true的未定义,引用符号&的使用等;

3、 栈的应用:逆序输出、语法检查、数制转换、递归等。

Monday, July 28, 2014