Stack和Queue——栈和队列
- 栈的定义:栈是限定仅在表头进行插入和删除操作的线性表(先进后出)
- 队列的定义:队列是一种特殊的线性表,特殊之处在于它只允许在表的前端(front)进行删除操作,而在表的后端(rear)进行插入操作,和栈一样,队列是一种操作受限制的线性表。进行插入操作的端称为队尾,进行删除操作的端称为队头。(先进先出)
stack常用函数:
- push()——向栈顶压入元素
- pop()——弹出栈顶元素
- top()——访问栈顶元素
queue常用函数:
- front()——访问队首元素
- back()——访问队尾元素
- push()——向队尾插入元素
- pop()——弹出队首元素
出栈顺序
题目描述:
有n个人,按照1,2,3...n的顺序依次进栈,判读能否以题目所给序列出栈。(n <= 100000)
eg:
- 4 3 2 1
- 1 2 3 4
- 1 3 2 4
- 1 4 2 3
| #include<bits/stdc++.h> |
| #define ios ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) |
| |
| using namespace std; |
| typedef long long LL; |
| const int N = 1e5 + 10; |
| int a[N]; |
| int n; |
| stack<int> stk; |
| int main() { |
| ios; |
| cin >> n; |
| for (int i = 1; i <= n; i++) { |
| cin >> a[i]; |
| } |
| int j = 1; |
| for (int i = 1; i <= n; i++) { |
| stk.push(i); |
| while (!stk.empty() && a[j] == stk.top()) { |
| stk.pop(); |
| j++; |
| } |
| } |
| |
| if (!stk.empty()) cout << "No"; |
| else cout << "Yes"; |
| |
| |
| return 0; |
| } |
思路:
如果栈顶元素比后面没入栈的元素都大,那么它就应该出栈
| #include<bits/stdc++.h> |
| #define ios ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) |
| |
| using namespace std; |
| typedef long long LL; |
| const int N = 1e6 + 10; |
| int a[N], maxn[N]; |
| int n; |
| stack<int> stk; |
| int main() { |
| ios; |
| cin >> n; |
| for (int i = 1; i <= n; i++) { |
| cin >> a[i]; |
| } |
| |
| |
| for (int i = n; i >= 1; i--) { |
| maxn[i] = max(a[i], maxn[i + 1]); |
| } |
| |
| for (int i = 1; i <= n; i++) { |
| stk.push(a[i]); |
| while (!stk.empty() && stk.top() > maxn[i + 1]) { |
| printf("%d ", stk.top()); |
| stk.pop(); |
| } |
| } |
| |
| |
| while (!stk.empty()) { |
| printf("%d ", stk.top()); |
| stk.pop(); |
| } |
| return 0; |
| } |
| #include<bits/stdc++.h> |
| #define ios ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) |
| |
| using namespace std; |
| typedef long long LL; |
| |
| string s; |
| stack<int> stk; |
| int main() { |
| ios; |
| cin >> s; |
| for (int i = 0; i < s.size(); i++) { |
| if (s[i] == 'a') { |
| stk.push('a'); |
| } else { |
| if (stk.empty()) { |
| cout << "Bad" << endl; |
| return 0; |
| } else { |
| stk.pop(); |
| } |
| } |
| } |
| |
| if (stk.empty()) cout << "Good"; |
| else cout << "Bad"; |
| return 0; |
| } |
思路:
思考易得,每次选择当前的果子数最少的两堆进行合并,花费的体力最少
维护两个队列
表示还没有合并的果子从小到大的序列
表示已经合并的果子的序列(自然从小到大,因为越合并果子数越大)
每次判断两个队列的队首元素大小,小的出列,合并完后放入
| #include<bits/stdc++.h> |
| #define ios ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) |
| |
| using namespace std; |
| typedef long long LL; |
| const int N = 1e5 + 10; |
| int a[N]; |
| int n; |
| queue<int> q1, q2; |
| int main() { |
| ios; |
| cin >> n; |
| for (int i = 1; i <= n; i++) { |
| cin >> a[i]; |
| } |
| sort(a + 1, a + 1 + n); |
| for (int i = 1; i <= n; i++) { |
| q1.push(a[i]); |
| } |
| |
| int ans = 0; |
| for (int i = 1; i < n; i++) { |
| int x[3]; |
| for (int j = 1; j <= 2; j++) { |
| if (q2.empty() || (!q1.empty() && q1.front() < q2.front())) { |
| x[j] = q1.front(); |
| q1.pop(); |
| } else { |
| x[j] = q2.front(); |
| q2.pop(); |
| } |
| } |
| ans += x[1] + x[2]; |
| q2.push(x[1] + x[2]); |
| } |
| cout << ans << endl; |
| return 0; |
| } |
优先队列写法:
| #include<bits/stdc++.h> |
| #define ios ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) |
| #define bug(x) cout<<#x<<"=="<<x<<endl; |
| using namespace std; |
| typedef long long LL; |
| |
| const int N = 1e6 + 10; |
| int n; |
| int a[N]; |
| priority_queue<int, vector<int>, greater<int> >q; |
| int main() { |
| ios; |
| cin >> n; |
| for (int i = 1; i <= n; i++) { |
| cin >> a[i]; |
| q.push(a[i]); |
| } |
| |
| LL ans = 0; |
| for (int i = 1; i < n; i++) { |
| int tmp1 = q.top(); |
| q.pop(); |
| int tmp2 = q.top(); |
| q.pop(); |
| ans += tmp1 + tmp2; |
| q.push(tmp1 + tmp2); |
| } |
| |
| cout << ans << endl; |
| return 0; |
| } |
题目描述:
给定一个长度为n的数列,求长度为k的定长连续子区间{},{}......中每个区间的最大值和最小值。
| #include<bits/stdc++.h> |
| #define ios ios::sync_with_stdio(false),cin.tie(0),cout.tie(0) |
| using namespace std; |
| typedef long long LL; |
| |
| const int N = 1e6 + 10; |
| int n, k; |
| int a[N]; |
| deque<int> maxn, minn; |
| |
| |
| int main() { |
| ios; |
| cin >> n >> k; |
| for (int i = 1; i <= n; i++) { |
| cin >> a[i]; |
| } |
| |
| for (int i = 1; i <= n; i++) { |
| if (!minn.empty() && i - minn.front() >= k) minn.pop_front(); |
| while (!minn.empty() && a[i] <= a[minn.back()]) { |
| minn.pop_back(); |
| } |
| minn.push_back(i); |
| if (i >= k) cout << a[minn.front()]; |
| } |
| |
| cout << endl; |
| |
| for (int i = 1; i <= n; i++) { |
| if (!maxn.empty() && i - maxn.front() >= k) maxn.pop_front(); |
| while (!maxn.empty() && a[i] >= a[maxn.back()]) { |
| maxn.pop_back(); |
| } |
| maxn.push_back(i); |
| if (i >= k) cout << a[maxn.front()]; |
| } |
| |
| |
| return 0; |
| } |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南