在之前写的C语言实现链式栈篇博文中,我已经给大家大概介绍了关于链式栈的意义以及相关操作,我会在下面给大家分享百度百科对链式栈的定义,以及给大家介绍利用C++实现链式栈的基本操作。

百度百科链式栈

链式栈是一种数据存储结构,可以通过单链表的方式来实现,使用链式栈的优点在于它能够克服用数组实现的顺序栈空间利用率不高的特点,但是需要为每个栈元素分配额外的指针空间用来存放指针域。

栈是只能在某一端插入和删除的特殊线性表。它按照后进先出的原则存储数据,先进入的数据被压入栈底(push),最后的数据在栈顶(top),需要读数据的时候从栈顶开始弹出数据(top)最后一个数据被第一个读出来。链式栈中的元素以Node的形式存储,节点Node中存有此节点存于栈中的元素以及指向下个节点的指针。链式栈的数据成员只用保存指向栈顶节点的指针 *top_node。

顺序栈的实现在于使用了数组这个基本数据结构,数组中的元素在内存中的存储位置是连续的,且编译器要求我们在编译期就要确定数组的大小,这样对内存的使用效率并不高,一来无法避免因数组空间用光而引起的溢出问题,二在系统将内存分配给数组后,则这些内存对于其他任务就不可用;而对于链栈而言,使用了链表来实现栈,链表中的元素存储在不连续的地址,由于是动态申请内存,所以我们可以以非常小的内存空间开始,另外当某个项不使用时也可将内存返还给系统。

C++实现链式栈

利用C++语言实现了数据结构的链式栈,主要完成了以下操作:

链式栈的 基本操作
元素进栈 元素出栈
返回栈顶元素 判断栈是否为空
打印栈的元素

链式栈的结点

链式栈的结点其实跟链式结构的顺序结构差不多类似,包含两部分,一是储存数据的数据域,二是储存下一结点地址的指针域,因此以结构体封装的结点如下:

template <class T>
struct chainStackNode
{
T data;//链式栈储存结点的数据
chainStackNode<T> *next;//链式栈指向下一结点的指针
};

链式栈的基本操作

在写这次链式栈的时候,我在所有的函数实现前都加上了inline,在这里给大家解释一下。inline是C++关键字,在函数声明或定义中,函数返回类型前加上关键字inline,即可以把函数指定为内联函数。这样可以解决一些频繁调用的函数大量消耗栈空间(栈内存)的问题。关键字inline必须与函数定义放在一起才能使函数成为内联函数,仅仅将inline放在函数声明前面不起任何作用。inline是一种“用于实现”的关键字,而不是一种“用于声明”的关键字。

构造函数

构造函数,就是实现成员的初始化操作,当然在这里实现链式栈的初始化就只需要创建一个头指针,并初始化头指针的各个成员。

template <class T>
inline chainStack<T>::chainStack()
{
top = new chainStackNode<T>;//创建一个新的结点
top->next = NULL;//将top的next指针指向空
}
元素进栈

链式栈的进栈操作,顾名思义就是一个新的元素进入栈,当然首先要创建一个新的结点,然后就是将这个新的结点插入到栈顶,只需要调整来两个指针操作。

template <class T>
inline bool chainStack<T>::Push(T newData)
{
chainStackNode<T> *newNode = new chainStackNode<T>;
if(!newNode){
cout<<"分配内存失败!"<<endl;
return false;
}
newNode->data = newData;//修改指针,添加元素
newNode->next = top->next;
top->next = newNode;
return true;
}
元素出栈

元素出栈,就跟线性表的删除元素类似,不过只能删除顶部结点,这个栈的特性是不可以违背的,调整指针删除结点之后不要忘了释放删除的结点的内存。

template <class T>
inline bool chainStack<T>::Pop(T &x)
{
chainStackNode<T> *temporaryNode;//创建一个临时指针指向删除结点
if(isEmpty() == true){
cout<<"该栈为空!"<<endl;
return false;
}
else
{
temporaryNode = top->next;
x = temporaryNode->data;//以引用返回
top->next = temporaryNode->next;
delete temporaryNode;//释放空间
return true;
}
}
返回栈顶元素

返回栈顶的元素,判断栈是否为空,如果为空自然没有元素可以返回,否则就返回top指向的下一个结点的数据即可。

template <class T>
inline bool chainStack<T>::getTop(T &x)
{
if(isEmpty() == true){
return false;
}
else{
x = top->next->data;
return true;
}
}
判断栈是否为空

有了top指针,就只需要判断top指针的下一结点是否为空即可。

template <class T>
inline bool chainStack<T>::isEmpty()
{
if(top->next == NULL){//top指针的下一结点是否为空,以此来判断是否为空
return true;
}
else{
return false;
}
}
打印栈的元素

打印栈的元素,就是一个遍历的过程,定义一个指针,输出结点数据,调整指针位置。

template <class T>
inline void chainStack<T>::printChainStackData()
{
chainStackNode<T> *pMove;
pMove = top->next;
while(pMove->next != NULL){
cout<<"["<<pMove->data<<"]->";
pMove = pMove->next;
}
cout<<"["<<pMove->data<<"]"<<endl;
}

到这里,利用C++语言实现链式栈的介绍就已经结束了,如果有哪里写的不好的地方,还希望大家给我提出了,我加以修正,完整的代码包括测试代码我已经push到了githubC++实现链式栈,另外如果大家还想了解其他的内容,欢迎来我的博客,我们一起讨论,共同进步!

C++语言实现链式栈的更多相关文章

  1. C语言数据结构-链式栈的实现-初始化、销毁、长度、取栈顶元素、查找、入栈、出栈、显示操作

    1.数据结构-链式栈的实现-C语言 //链式栈的链式结构 typedef struct StackNode { int data; struct StackNode *next; } StackNod ...

  2. go语言实现链式栈

    haa哈哈== import "errors" var ( // ErrEmpty 栈为空 ErrEmpty = errors.New("stack is empty&q ...

  3. C语言链表全操作(增,删,改,查,逆序,递增排序,递减排序,链式队列,链式栈)

    一,数据结构——链表全操作: 链表形式: 其中,每个节点(Node)是一个结构体,这个结构体包含数据域,指针域,数据域用来存放数据,指针域则用来指向下一个节点: 特别说明:对于单链表,每个节点(Nod ...

  4. 栈(链式栈)----C语言

    链式栈:就是一种操作受限的单向链表,对单向链表还不了解的可先看一下之前的一篇关于单向链表的随笔,链表(单向链表的建立.删除.插入.打印),理解了单向链表后再来看链式栈就比较轻松了 链式栈的操作一般含有 ...

  5. 链式栈-C语言实现

    相对于顺序栈的空间有限,链式栈的操作则更加灵活 #include<stdio.h> #include<malloc.h> typedef int SElemType; //元素 ...

  6. C++学习(三十七)(C语言部分)之 链式栈(推箱子实现)

    用链表实现栈一开始在表头插入,就要一直在表头插入一开始在表尾插入,就要一直在表头插尾表头当栈底 也可以把表尾当栈底 实现的测试代码笔记如下: #include<stdio.h> #incl ...

  7. 传智播客C语言视频第二季(第一季基础上增加诸多C语言案例讲解,有效下载期为10.5-10.10关闭)

    卷 backup 的文件夹 PATH 列表卷序列号为 00000025 D4A8:14B0J:.│  1.txt│  c语言经典案例效果图示.doc│  ├─1传智播客_尹成_C语言从菜鸟到高手_第一 ...

  8. 传智播客C语言视频第一季(有效下载期为10.1-10.7,10.8关闭)

     J:\传智播客_尹成_C语言从菜鸟到高手├─传智播客_尹成_C语言从菜鸟到高手_第一章C语言概述A│      第一讲1.1C语言第一阶段.mp4│      第二讲1.2c语言入门教程.mp4 ...

  9. [数据结构]C语言栈的实现

    有始有终,所以我准备把各种数据结构都讲一次,栈也分顺序存储和链式储存,这里我们选择链式存储来讲,顺序存储没有难度(链式其实也是) 作为数据结构中最简单的栈,这里不会说太多,首先考虑一下下面的model ...

随机推荐

  1. 【Java面试题】List如何一边遍历,一边删除?

    这是最近面试时被问到的1道面试题,本篇博客对此问题进行总结分享. 1. 新手常犯的错误 可能很多新手(包括当年的我,哈哈)第一时间想到的写法是下面这样的: public static void mai ...

  2. 关于WPF System.windows.Media.FontFamily 的类型初始值设定项引发异常问题解决方法

    造成原因:此问题的根本原因是.NET Framework January 2018 Rollup(KB4055002)与已安装的.NET Framework 4.7.1产品版本之间的MSI安装交互.R ...

  3. 网络安全从入门到精通 ( 第二章-5) 后端基础PHP—简介及基本函数-下

    本文内容: 循环语句 PHP获取表单信息 PHP操作Mysql语句 语法SQL注入 1,循环语句: for循环: 语法:for($x=0,$x<10;$x++){执行语句;} 注意:$x++,先 ...

  4. Natas4 Writeup(Referer篡改)

    Natas4: 提示来源出错,合法用户只能来自"http://natas5.natas.labs.overthewire.org/". 在http的header中,referer代 ...

  5. uni-app 遮罩模板

    1. common新建mask.vue文件. <template> <view> <view class="cpt-mask"> </vi ...

  6. Android AlertDialog 各种弹框代码

    1.消息框 btn01.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { ...

  7. jwt(JSON Web Tokens)的一道题目代码分析

    题目链接https://github.com/wonderkun/CTF_web/tree/5b08d23ba4086992cbb9f3f4da89a6bb1346b305/web300-6 参考链接 ...

  8. 软件版本管理工具-SVN

    一.SVN简介 Subversion(svn)是一款开发源代码的版本控制系统. repository(源代码库):源代码统一存放的地方 Checkout(检出):当你手上没有源代码的时候,你需要从re ...

  9. django-jwt token校验源码简析

    一. jwt token校验源码简析 1.1 前言 之前使用jwt签发了token,里面的头部包含了加密的方式.是否有签名等,而载荷中包含用户名.用户主键.过期时间等信息,最后的签名还使用了摘要算法进 ...

  10. Django之CBV装饰器,跨站请求伪造,auth认证

    CBV加装饰器 基于session实现登录 def login(request): if request.method == 'POST': username = request.POST.get(' ...