1 栈的定义

栈是只允许一端进行插入或删除的线性表
栈_第1张图片

1.1 栈的基本操作:

  • InitStack(&S):初始化栈。构造一个空栈S,分配内存空间
  • DestroyStack(&L):销毁栈。销毁并释放栈S所占用的内存空间
  • Push(&S,x):进栈,若栈S未满,则将新进栈的元素作为新栈顶
  • Pop(&S,&x):出栈,若栈S非空,则弹出栈顶元素,并用x返回
  • GetTop(S,&x):读栈顶元素,若栈S非空,则用x返回栈顶元素
  • StackEmpty(S):判断一个栈S是否为空。若S为空,则返回true,否则返回true

2 顺序栈

2.1 顺序栈的定义实现

#define MaxSize 10
typdef struct {
	ElemType data[MaxSize];// 存放栈中元素
	int top;// 栈顶指针
}SqStack;

2.2 初始化操作

void InitStack(SqStack &S){
	s.top = -1;// 初始化栈顶指针
}

2.3 进栈操作

栈_第2张图片

bool Push(SqStack &S,ElemType x) {
	if(S.top == MaxSize-1)// 栈满
		return false;
	S.data[++top] = x;// 指针先向上移动一位,再赋值
	return true;
}

2.4 出栈操作

栈_第3张图片

bool Pop(SqStack &S,ElemType &x) {
	if(S.top == -1)// 栈空
		return false;
	x = S.data[top--];// 先把值保存给x,再将指针向下移动
	return true;
}

2.5 共享栈

两个栈共享一片空间的叫做共享栈。
栈_第4张图片

  • 定义
#define MaxSize 10
typedef struct {
	ElemType data[MaxSize];
	int top0;// 0号栈
	int top1;// 1号栈
}ShStack;
  • 初始化
void InitStack(ShStack &S) {
	s.top0 = -1;// 初始化栈顶指针
	s.top1 = MaxSize;
}
  • 栈满条件:s.top0+1 == s.top1

3 链栈:操作跟链表差不太多,只不过被限制在头结点后处操作

3.1 定义

用链式存储实现的栈

typedef struct LinkNode{
	ElemType data;
	struct LinkNode *next;
}*LiStack

3.2 初始化操作

bool InitLiStack(LiStack &L) {
	L = (LinkNode*)malloc(sizeof(LinkNode));
	if(L == Null){
		return false;
	}
	L->next = Null;
	return L:
}

3.3 出栈操作:仅仅在头结点后处操作

bool LiStackDelete(LiStack &L,ElmeType &e) {
	if(L->next == Null) {
		return false;
	}
	LNode *q = L->next;
	e = q->data;
	q->next = L->next;
	free(q);
	return q;
}

3.4 进栈操作:仅仅在头结点后处操作

bool LiStackInsert(LiStack &L,ElmeType e) {
	LNode *q = (LNode *)malloc(sizeof(LNode));
	if(q == Null) {
		return false;
	}
	q->data = e;
	q->next = L->next;
	L->next = q;
	return true;
}

3.5 读取栈顶元素操作

bool GetTop(LiStack S,&x) {
	if(S->next == Null) {
		return false;
	}
	x = S->next->data;
	return true;
}

3.6 栈空,不考虑栈满

bool StackEmpty(LiStack S){
		if(S->next == Null) return true;
		else return false;
}

4 栈的应用

4.1 括号匹配

4.1.1 问题描述

假设表达式中允许包含两种括号:()、[],其嵌套的顺序任意即([])、[()]均可。[()、((())均为不正确格式。简单来说就是要匹配上“(”要匹配上“)”、“[“要匹配上”]”。

4.1.2 算法描述

栈_第5张图片

  1. 初始设置一个空栈,顺序读入括号
  2. 若是右括号,则使将栈顶元素登出得以匹配,或者不匹配,则退出程序
  3. 若是左括号则入栈。算法结束时,栈为空,否则括号匹配失败
    栈_第6张图片

4.1.3 代码实现

// 定义
#define MaxSize 10
typedef struct {
	char data[MaxSize];
	int top;
}SqStack;
// 初始化
void InitStack(SqStack &S);
// 判空
bool StackEmpty(SqStack S);
// 入栈
bool Push(SqStack &S,char x);
// 出栈
bool Pop(SqStack &S,char &x);
// 匹配
bool bracketCheck(char str[],int length) {
	SqStack S;
	InitStack(S);
	for(int i = 0; i <lenght; i++) {// 顺序扫描
		if(str[i] == '('|| str[i] == '[' ) {
			Push(S,str[i]);
		}else{
			if(StackEmpty(S)) return false;
			char topElem;
			Pop(S,topElem);
			if(str[i] == ')' && topElem!='(')
				return false;
			if(str[i] == ']' && topElem!='[')
				return false;
		}
	}
}

4.2 表达式求值

4.2.1 概念

算式表达式由操作数、运算符、界限符组成。
栈_第7张图片

4.2.2 中缀转后缀

转换思路:
栈_第8张图片例子:
栈_第9张图片转换思路(机算):
栈_第10张图片

后缀表达式的计算方法(手算):

栈_第11张图片后缀表达式的计算方法(机算):
栈_第12张图片

4.2.3 中缀转前缀

转换思路:
栈_第13张图片

前缀表达式的计算方法(机算):
栈_第14张图片

4.2.4 中缀表达式的计算

栈_第15张图片

4.3 在递归上的应用

你可能感兴趣的:(数据结构,数据结构)