C++用栈实现先入先出队列相关知识与代码实现
1、栈(stack)的基本知识
C++的栈是一种数据结构,它是一个后进先出(LIFO)的线性结构,具有两个基本操作:push和pop。
push操作将数据压入栈顶,而pop操作将栈顶数据弹出。
C++中的栈实现在STL中,可以使用std::stack来创建一个栈。
std::stack可以被视为一种容器适配器,它基于其他容器实现,
例如std::deque和std::list。
适用场景:
在C++中,栈通常用于实现函数调用堆栈和表达式求值等场景。当一个函数被调用时,它的返回地址和其他必要数据被压入栈中,当函数返回时,这些数据被弹出。
基本存储方式:
(1)顺序存储:利用一段连续的内存空间进行存储。
(2)链式存储:利用非连续的内存空间存储,元素之间使用指针进行链接。(通常单链表实现,栈顶是表头,栈底的表尾)。
构造函数:
构造函数原型 | 解释 | |
1 | stack<T> stk | 默认构造 |
2 | stack(const stack &stk) | 拷贝构造 |
赋值操作:
函数原型:= | 解释 | |
1 | stack& operator=(const stack &stk) | 重载=操作符 |
数据存取:
函数原型:push、pop、top | 解释 | |
1 | push(elem) | 入栈:向栈顶添加元素 |
2 | emplace() | 入栈:构造和添加元素 |
3 | pop() | 出栈:移除当前栈顶元素 |
4 | top() | 返回栈顶元素 |
push与emplace的异同点:
- 对于int、double等内置数据类型而言,
push()
和emplace()
是相同的
- 对于自定义数据类型而言,使用
push()
前必须先将要添加的对象构造出来(实例化),而使用emplace()
既可以填入实例化的对象也可以填入对象的构造参数
2、栈(stack)的相关术语和基本操作
栈顶(top):
线性表允许插入和删除的那一段。值得注意的是,栈顶指针top的指向是有些两种方式的,一种是指向栈顶当前元素,一种是指向栈顶的下一位置。
栈底(bottom):
固定的,不允许进行插入和删除的另一端。
空栈:
不含有任何元素的空表。
基本操作:
(1)栈判空:
1 bool isEmpty(SqStack S)
2 {
3 if (S.top==-1)
4 {
5 return true;
6 }
7 return false;
8 }
(2)栈判满
1 bool isFull(SqStack S)
2 {
3 if (S.top == MAXSIZE - 1)
4 {
5 return true;
6 }
7 return false;
8 }
(3)入栈
1 bool Push(SqStack& S, ElemType e)
2 {
3 bool flag = isFull(S);
4 if (flag==true)
5 {
6 printf("栈满\n");
7 return false;
8 }
9 S.top++;
10 S.data[S.top] = e;
11 return true;
12
13 }
(4)出栈
1 bool Pop(SqStack& S, ElemType& e)
2 {
3 bool flag = isEmpty(S);
4 if (flag)
5 {
6 printf("栈空\n");
7 return false;
8 }
9 e = S.data[S.top];
10 S.top--;
11 return true;
12 }
(5)取栈顶
1 //取栈顶
2 bool GetTop(SqStack& S, ElemType& e)
3 {
4 bool flag = isEmpty(S);
5 if (flag)
6 {
7 return false;
8 }
9 e = S.data[S.top];
10 return true;
11 }
(6)初始化一个空栈
InitStack(&s);
(7)判断一个在栈是否为空
StackEmpty(s);
3、栈的代码测试
1 int _tmain(int argc, _TCHAR* argv[])
2 {
3 ArrayStack <int> p(5);
4 for (int i = 0; i < 5; i++)
5 {
6 p.push(i);
7 }
8 cout << "栈的大小:"<<p.size() << endl;
9 cout << "栈是否为空:"<<p.isEmpty() << endl;
10 cout << "栈顶元素:"<<p.top() << endl;
11 cout << "依次出栈:" << endl;
12 while (!p.isEmpty())
13 {
14 cout << p.pop() << endl;
15 }
16 getchar();
17 return 0;
18 }
4、队列的基本知识
- 与栈相比,栈是先进后出,队列中的数据元素遵循“先进先出”(First In First Out)的原则,简称FIFO结构。
- 在队尾添加元素,在队头删除元素。
队列(queue)的结构如下:类似于生活中的排队买票,最先排队的人位于队伍最前端,后来的人依次从队伍末尾加入队伍。当队首的人买票成功后离开,原先位于第二位的人顶上成为新的队首,后续以此类推。
相关术语 :
(1)入队:队列的插入操作。 允许插入数据的位置叫队尾
(2)出队:队列的删除操作。 允许删除数据的位置叫队头
操作:
- 入队: 通常命名为push()
- 出队: 通常命名为pop()
queue构造函数:
构造函数原型 | 解释 | |
1 | queue<T> que | 默认构造 |
2 | queue(const queue &que) | 拷贝构造 |
queue赋值操作:
函数原型:= | 解释 | |
1 | queue& operator =(const queue &que) | 重载 = 操作符 |
queue数据存取:
函数原型:push、pop、back、front | 解释 | |
1 | push(elem) | 向队尾添加队尾 |
2 | emplace() | 向队尾添加元素 |
3 | pop() | 移除当前队首元素 |
4 | back() | 返回队尾元素 |
5 | front() | 返回队首元素 |
queue其他操作:
函数原型:empty、size、swap | 解释 | |
1 | empty() | 判断队列是否为空 |
2 | size() | 返回队列的大小 |
3 | swap(queue<T> & que) | 将当前队列中元素和que中元素交换 |
5、整体所需操作
队列
1 queue<int> q; //定义一个空队列q
2
3 push(x) -- 将一个元素放入队列的尾部。
4 pop() -- 从队列首部移除元素。
5 peek() -- 返回队列首部的元素。//同front()
6 empty() -- 返回队列是否为空。
7 back()访问队尾元素
8 size()访问队中的元素个数
栈
1 stack<int> s;
2
3 push(x) -- 元素 x 入栈
4 pop() -- 移除栈顶元素
5 top() -- 获取栈顶元素
6 empty() -- 返回栈是否为空
6、用栈实现队列代码解释
官方:
将一个栈当作输入栈,用于压入 push传入的数据;另一个栈当作输出栈,用于 pop和 peek操作。
每次 pop或 peek时,若输出栈为空则将输入栈的全部数据依次弹出并压入输出栈,这样输出栈从栈顶往栈底的顺序就是队列从队首往队尾的顺序。
1 class MyQueue {
2 private:
3 stack<int>inStack, outStack;
4
5 void in2out(){
6 while (!inStack.empty()) {
7 outStack.push(inStack.top());
8 inStack.pop();
9 }
10 }
11
12 public:
13 MyQueue() {
14
15 }
16
17 void push(int x) {
18 inStack.push(x);
19 }
20
21 int pop() {
22 if (outStack.empty()){
23 in2out();
24 }
25
26 int x = outStack.top();
27 outStack.pop();
28 return x;
29
30 }
31
32 int peek() {
33 if (outStack.empty()){
34 in2out();
35 }
36 return outStack.top();
37
38 }
39
40 bool empty() {
41 return inStack.empty() && outStack.empty();
42
43 }
44 };
45
46 /**
47 * Your MyQueue object will be instantiated and called as such:
48 * MyQueue* obj = new MyQueue();
49 * obj->push(x);
50 * int param_2 = obj->pop();
51 * int param_3 = obj->peek();
52 * bool param_4 = obj->empty();
53 */
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)