一、栈相关知识点
1.定义:
一种可以实现”先进后出“的数据结构。只允许在一端进行插入或删除操作的线性表。栈是一种线性表,但限定了这种线性表只能在某一端进行插入和删除操作。
- 栈顶(top):线性表允许进行插入删除的那一端
- 栈底(bottom):固定的,不允许进行插入和删除的那一端
- 空栈:不含任何元素的空表
2.分类:
静态栈:以数组为内核,即栈内部存储数据的空间是连续的,且预先分配内存空间,内存满了无法继续入栈,好处是数组为内核方便数据操作。
动态栈:以链表为内核,即栈内部存储数据的空间是离散的,只要内存足够,就可以一直入栈。
3.应用:
函数调用、中断、表达式求值、缓冲处理、迷宫等。
4.算法(以动态栈为例):
Ⅰ:压栈(也称入栈),即将数据在尾部插入,其伪算法如下:
①:创建一个新节点t,保存插入的val值
t.val = val
②:将节点t的指针域指向Ptop
t.p = Ptop->p
③:更新栈顶指针Ptop,指向节点t
Ptop = t
Ⅱ:出栈,即将顶部数据取出并释放,其伪算法如下:
①:创建一个新节点t,临时保存需要取出的数据。一是为了返回取出的数据val,而是防止内存泄露,在delete释放时通过t才能找到这块内存
t = Ptop;
val = t.val;
②:更新栈顶指针
Ptop = Ptop->p;
③释放出栈的节点内存
delete t;
二、c++实现动态栈
1.构建节点类
#include<iostream>
#include<string>
using namespace std;
//定义节点
class NODE {
public:
NODE() {
this->data = 0;
this->pnext = nullptr;
}
NODE* pnext;
int data;
};
2.构建栈类,并通过构造函数初始化,使栈顶栈底指向同一个节点,
class STACK{
public:
STACK() {
this->len = 0;
NODE* t = new NODE();
this->pbottom = t;
this->ptop = t;
};
private:
int len;
NODE* ptop;
NODE* pbottom;
};
3.在类中实现判空、入栈、出栈和遍历功能
//判空
bool empty() {
if (this->pbottom == this->ptop) return true;
else return false;
}
//入栈
void push(int val) {
NODE* t = new NODE();
t->data = val;
t->pnext = this->ptop;
this->ptop = t;
len++;
return;
}
//出栈
int pop() {
if(this->empty()!=true){
NODE* t = this->ptop;
int val = t->data;
this->ptop = this->ptop->pnext;
delete t;
len--;
return val;
}
}
//遍历
void travel() {
NODE* t = this->ptop;
cout << "栈中数据为: ";
while (t!=this->pbottom) {
cout << t->data << " ";
t = t->pnext;
}
cout << endl;
return;
}
4.测试:将1 2 3分别入栈后遍历,再出栈一次进行遍历
void test() {
STACK stack1;
stack1.push(1);
stack1.push(2);
stack1.push(3);
stack1.travel();
int val = stack1.pop();
cout << "出栈的值为:" << val << endl;
stack1.travel();
return;
}
5.测试结果
三、全部代码
#include<iostream>
#include<string>
using namespace std;
//定义节点
class NODE {
public:
NODE() {
this->data = 0;
this->pnext = nullptr;
}
NODE* pnext;
int data;
};
//定义栈
class STACK{
public:
STACK() {
this->len = 0;
NODE* t = new NODE();
this->pbottom = t;
this->ptop = t;
};
~STACK() {
};
//判空
bool empty() {
if (this->pbottom == this->ptop) return true;
else return false;
}
//入栈
void push(int val) {
NODE* t = new NODE();
t->data = val;
t->pnext = this->ptop;
this->ptop = t;
len++;
return;
}
//出栈
int pop() {
if(this->empty()!=true){
NODE* t = this->ptop;
int val = t->data;
this->ptop = this->ptop->pnext;
delete t;
len--;
return val;
}
}
//遍历
void travel() {
NODE* t = this->ptop;
cout << "栈中数据为: ";
while (t!=this->pbottom) {
cout << t->data << " ";
t = t->pnext;
}
cout << endl;
return;
}
private:
int len;
NODE* ptop;
NODE* pbottom;
};
void test() {
STACK stack1;
stack1.push(1);
stack1.push(2);
stack1.push(3);
stack1.travel();
int val = stack1.pop();
cout << "出栈的值为:" << val << endl;
stack1.travel();
return;
}
void main() {
test();
return;
}