IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 数据结构与算法 -> 数据结构——线性表——栈 -> 正文阅读

[数据结构与算法]数据结构——线性表——栈

目录

一、栈

1.栈的定义

2.栈的分类

二、栈的顺序存储结构

1.顺序栈的定义

2.顺序栈是四要素

3.顺序栈的基本运算算法

(1)代码部分

(2)结果演示

三、栈的链式存储结构

1.链栈的定义

?2.链栈的四要素

3.链栈的基本运算算法

(1)代码部分

(2)结果演示

四、实例讲解

1.判断一个字符串是否为回文。

2.进制转换

五、总结


一、栈

1.栈的定义

栈是只能从一端存取数据和读取数据且遵循 "先进后出" 或“后进后出”原则的线性存储结构。

2.栈的分类

与线性表存储结构类似,栈也有两种存储结构:顺序存储结构和链式存储结构。

二、栈的顺序存储结构

1.顺序栈的定义

顺序栈:即用顺序存储结构方式设计栈的存储数据,从而实现栈存储结构。

顺序栈通常有一个一维数组data和一个记录栈顶元素位置的变量top组成,底部称为栈底,头部称为栈顶。如图所示:

2.顺序栈是四要素

设顺序栈为st.

(1)栈空:st.top==-1。

(2)栈满条件:st.top==MaxSize-1。

(3)元素x进栈操作:st.top++;将元素x放在st.data[st.top]中。

(4)出栈元素x操作:取出栈元素x=st.data[st.top];st.top--

3.顺序栈的基本运算算法

a:void InitStack()? //初始化顺序栈

b:void DestroyStack()? ?//销毁顺序栈

c:int Push()? //进栈操作

d:int Pop()? ? //出栈操作

e:int GetTop()? //取栈顶元素运算

f:int StackEmpty()? //判断栈是否为空

(1)代码部分

#include<stdio.h>
typedef char ElemType;
//顺序栈的声明
#define MaxSize 200     //定义全局变量
typedef struct
{
	ElemType data[MaxSize];
	int top;
}SequenceStack;
//初始化
void InitStack(SequenceStack &st)
{
	st.top=-1;  //设计栈顶
}
//销毁
void DestroyStack(SequenceStack st)
{
}  //由于顺序栈的内存空间是有系统自由分配的,故系统也会自动释放其空间
//进栈
int Push(SequenceStack &st,ElemType x)
{
	if(st.top==MaxSize-1)
		return 0;           //栈满
	else 
	{
		st.top++;
		st.data[st.top]=x;
		return 1;            //成功进栈
	}
}
//出栈

int Pop(SequenceStack &st,ElemType &x)
{
	if(st.top==-1)
	return 0;             //栈空
	else
	{
		x=st.data[st.top];
		st.top--;
		return 1;           //成功出栈
	}
}

//取栈顶元素运算
int GetTop(SequenceStack st,ElemType &x)
{
	if(st.top==-1)
		return 0;         //栈空
	else
	{
		x=st.data[st.top];
		return 1;     //成功去栈顶元素
	}
}
//判断栈空运算算法
int StackEmpty(SequenceStack st)
{
	if(st.top==-1)
		return 1;    //栈空
	else
		return 0;    //栈不空
}

void main()
{
	SequenceStack st;
	ElemType e;
	printf("初始化栈st\n");
	InitStack(st);
	printf("栈%s\n",(StackEmpty(st)==1 ?"空" : "不空"));
	printf("a进栈\n");
	Push(st,'a');
	printf("b进栈\n");
	Push(st,'b');
	printf("c进栈\n");
	Push(st,'c');
	printf("d进栈\n");
	Push(st,'d');
	printf("e进栈\n");
	Push(st,'e');
	printf("f进栈\n");
	Push(st,'f');
	printf("栈%s\n",(StackEmpty(st)==1 ?"空" : "不空"));
	GetTop(st,e);
	printf("栈顶元素:%c\n",e);
	printf("出栈次序:");
	while(!StackEmpty(st))
	{
		Pop(st,e);
		printf("%c",e);
	}
	printf("\n");
	DestroyStack(st);
}

(2)结果演示

三、栈的链式存储结构

1.链栈的定义

采用链式存储结构存储的栈称为链栈。本文采用单链表存储。如图所示:

?2.链栈的四要素

(1)栈空条件:s->next=NULL

(2)栈满条件:不考虑

(3)进制操作:将包含e结点插入到头结点之后

(4)出栈操作:取出头结点之后结点是元素并删除之。

3.链栈的基本运算算法

(1)代码部分

#include <stdio.h>
#include<malloc.h>
typedef char ElemType;
//链栈声明
typedef struct node
{
	ElemType data;
	struct node *next;     //指针域
}LinkStack;
//初始化
void InitStcak(LinkStack *&s)
{
	s=NULL; //空栈
}
//销毁
void DestroyStack(LinkStack *&s)
{
	LinkStack *pre=s,*p;
	if(pre==NULL)       //空栈
		return ;
	p=pre->next;
	while(p!=NULL)
	{
		free(pre);   //释放pre结点
		pre=p;
		p=p->next;
	}
	free(pre);      //释放尾结点
}
//进栈
int Push(LinkStack *&s,ElemType x)
{
	LinkStack *p;
	p=(LinkStack *)malloc(sizeof(LinkStack));
	p->data=x;       //插入p结点作为栈顶结点
	p->next=s;
	s=p;
	return 1;
}
//出栈
int Pop(LinkStack *&s,ElemType &x)
{
	LinkStack *p;
	if(s==NULL)       //栈空返回0
		return 0;
	else               //栈不空
	{
		p=s;           //p指向栈顶结点
		x=p->data;      //取栈顶运算x
		s=p->next;     //删除结点p
		free(p);        
		return 1;
	}
}
//取栈顶元素运算
int GetTop(LinkStack *s,ElemType &x)
{
	if(s==NULL)
		return 0;         //栈空
	else
	{
		x=s->data;    //栈不空
		return 1;
	}
}
//判断栈空
int StackEmpty(LinkStack *s)
{
	if(s==NULL)
		return 1;
	else
		return 0;
}

void main()
{
	ElemType e;
	LinkStack *st;
	printf("初始化st\n");
	printf("栈%s\n",(StackEmpty(st)==1 ?"空":"不空"));
	printf("a进栈\n");
	Push(st,'a');
	printf("b进栈\n");
	Push(st,'b');
	printf("c进栈\n");
	Push(st,'c');
	printf("e进栈\n");
	Push(st,'e');
	printf("d进栈\n");
	Push(st,'d');
	printf("f进栈\n");
	Push(st,'f');
	printf("栈%s\n",(StackEmpty(st)==1 ?"空":"不空"));
	GetTop(st,e);
	printf("栈顶元素:%c\n",e);
	printf("出栈次序:");
	while(!StackEmpty(st))
	{
		Pop(st,e);
		printf("%c",e);
	}
	printf("\n");
	DestroyStack(st);
}

(2)结果演示
?

四、实例讲解

1.判断一个字符串是否为回文。

分析:回文是指一个字符串str从前面度和从后面都一样,将字符串str颠倒输出并保持到另一个字符串str2中,如何通过比较字符串str和字符串str2是否一一对应即可判断是否为回文。

由于顺序栈的特点是先进后出,故将字符串str从头到尾的各个字符依次进栈便可得到一个颠倒后是字符串;然后将字符串str从头到尾的各个字符依次与从栈顶到栈底的各个字符比较即可,如果两者都相同,则str是回文,否则不是。

代码详解

int Palindrome(char str[],int strSize)
{
	SequenceStack st;         //定义一个顺序栈st
	InitStack(st);
	int i;
	char str2;
	for(i=0;i<n;i++)
		Push(st,str[i]);
	i=0;
	while(!StackEmpty(st))     //比较字符
	{
		Pop(st,ch);
		if(str2!=str[i++])
		{
			DestroyStack(st);
			return 0;
		}
	}
	DestoryStack(st);
	return 1;
}

2.进制转换

本例一十进制转十六进制为例。

分析:采用辗转相除法求余数,并将余数进栈暂存与顺序栈中,最后通过出栈输出十六进制数即可

代码详解:

void tranfroms(int n,char a[])
{
	SequenceStack st;
	InitStack(st);
	char ch;
	int i=0;
	while(a!=0)
	{
		ch='0'+n%2;
		Push(st,ch);
		n/=2;
	}
	while(!StackEmpty(st))
	{
		Pop(st,ch);
		a[i]=ch;
		i++;
	}
	a[i]='\0';
	DestroyStack(st);
}

五、总结

栈是线性表中特殊的存在,具有先进后出、后进先出的特点,可以快速有效的分配存储方式,可以实现很多功能。

  数据结构与算法 最新文章
【力扣106】 从中序与后续遍历序列构造二叉
leetcode 322 零钱兑换
哈希的应用:海量数据处理
动态规划|最短Hamilton路径
华为机试_HJ41 称砝码【中等】【menset】【
【C与数据结构】——寒假提高每日练习Day1
基础算法——堆排序
2023王道数据结构线性表--单链表课后习题部
LeetCode 之 反转链表的一部分
【题解】lintcode必刷50题<有效的括号序列
上一篇文章      下一篇文章      查看所有文章
加:2022-01-29 23:20:21  更:2022-01-29 23:20:23 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 19:36:09-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码