网站运营需要什么行业技术,wordpress公共课,广州做网站网络公司,金昌北京网站建设C第二阶段——数据结构和算法#xff0c;之前学过一点点数据结构#xff0c;当时是基于Python来学习的#xff0c;现在基于C查漏补缺#xff0c;尤其是树的部分。这一部分计划一个月#xff0c;主要利用代码随想录来学习#xff0c;刷题使用力扣网站#xff0c;不定时更… C第二阶段——数据结构和算法之前学过一点点数据结构当时是基于Python来学习的现在基于C查漏补缺尤其是树的部分。这一部分计划一个月主要利用代码随想录来学习刷题使用力扣网站不定时更新欢迎关注 文章目录 一、用栈实现队列力扣232二、用队列实现栈力扣225三、有效的括号力扣20四、 删除字符串中的所有相邻重复项力扣1047五、逆波兰表达式求值力扣150六、滑动窗口最大值力扣239七、前 K 个高频元素力扣347 一、用栈实现队列力扣232 请你仅使用两个栈实现先入先出队列。队列应当支持一般队列支持的所有操作push、pop、peek、empty 实现 MyQueue 类 void push(int x) 将元素 x 推到队列的末尾 int pop() 从队列的开头移除并返回元素 int peek() 返回队列开头的元素 boolean empty() 如果队列为空返回 true 否则返回 false 说明 你 只能 使用标准的栈操作 —— 也就是只有 push to top, peek/pop from top, size, 和 is empty 操作是合法的。 你所使用的语言也许不支持栈。你可以使用 list 或者 deque双端队列来模拟一个栈只要是标准的栈操作即可。 示例 1 输入 [“MyQueue”, “push”, “push”, “peek”, “pop”, “empty”] [[], [1], [2], [], [], []] 输出 [null, null, null, 1, 1, false] 解释 MyQueue myQueue new MyQueue(); myQueue.push(1); // queue is: [1] myQueue.push(2); // queue is: [1, 2] (leftmost is front of the queue) myQueue.peek(); // return 1 myQueue.pop(); // return 1, queue is [2] myQueue.empty(); // return false class MyQueue {
public:MyQueue() {}// 两个栈配合实现队列stackint s1;stackint s2;void push(int x) {s1.push(x);updateS2(s1,s2);}int pop() {int result s2.top();s2.pop();updateS1(s1,s2);return result;}int peek() {return s2.top();}bool empty() {if(s2.size()0){return true;}return false;}// 更新s2void updateS2(stackint s1,stackint s2){// 先将s2清空再将s1中所有元素添加到s2中int s2Size s2.size();for(int i0;is2Size;i){s2.pop();}// 将s1中所有元素添加到s2中int s1Size s1.size();for(int i0;is1Size;i){int temp s1.top();s2.push(temp);s1.pop();}}void updateS1(stackint s1,stackint s2){// 先将s1清空再将s2中所有元素添加到s1中int s1Size s1.size();for(int i0;is1Size;i){s1.pop();}// 将s1中所有元素添加到s2中int s2Size s2.size();for(int i0;is2Size;i){int temp s2.top();s1.push(temp);s2.pop();}}
};/*** Your MyQueue object will be instantiated and called as such:* MyQueue* obj new MyQueue();* obj-push(x);* int param_2 obj-pop();* int param_3 obj-peek();* bool param_4 obj-empty();*/二、用队列实现栈力扣225 请你仅使用两个队列实现一个后入先出LIFO的栈并支持普通栈的全部四种操作push、top、pop 和 empty。 实现 MyStack 类 void push(int x) 将元素 x 压入栈顶。 int pop() 移除并返回栈顶元素。 int top() 返回栈顶元素。 boolean empty() 如果栈是空的返回 true 否则返回 false 。 注意你只能使用队列的基本操作 —— 也就是 push to back、peek/pop from front、size 和 is empty 这些操作。 你所使用的语言也许不支持队列。 你可以使用 list 列表或者 deque双端队列来模拟一个队列 , 只要是标准的队列操作即可。 示例 输入 [“MyStack”, “push”, “push”, “top”, “pop”, “empty”] [[], [1], [2], [], [], []] 输出 [null, null, null, 2, 2, false] 解释 MyStack myStack new MyStack(); myStack.push(1); myStack.push(2); myStack.top(); // 返回 2 myStack.pop(); // 返回 2 myStack.empty(); // 返回 False class MyStack {
public:MyStack() {}// 使用一个队列完成queueint q;void push(int x) {q.push(x);}int pop() {// 将前面的重新添加到队列尾端int qSize q.size()-1;for(int i0;iqSize;i){q.push(q.front());q.pop();}int result q.front();q.pop();return result;}int top() {return q.back();}bool empty() {if(q.size()0){return true;}return false;}
};/*** Your MyStack object will be instantiated and called as such:* MyStack* obj new MyStack();* obj-push(x);* int param_2 obj-pop();* int param_3 obj-top();* bool param_4 obj-empty();*/三、有效的括号力扣20 给定一个只包括 ‘(’‘)’‘{’‘}’‘[’‘]’ 的字符串 s 判断字符串是否有效。 有效字符串需满足 左括号必须用相同类型的右括号闭合。 左括号必须以正确的顺序闭合。 每个右括号都有一个对应的相同类型的左括号。 示例 1 输入s “()” 输出true 示例 2 输入s “()[]{}” 输出true 示例 3 输入s “(]” 输出false 提示 1 s.length 104 s 仅由括号 ‘()[]{}’ 组成 class Solution {
public:bool isValid(string s) {if(s.length()%2!0) return false;stackchar st;for(int i0;is.length();i){if(s[i]() st.push());else if(s[i][) st.push(]);else if(s[i]{) st.push(});else if(st.empty()||s[i]!st.top()) return false;else st.pop();}return st.empty();}};四、 删除字符串中的所有相邻重复项力扣1047 给出由小写字母组成的字符串 S重复项删除操作会选择两个相邻且相同的字母并删除它们。 在 S 上反复执行重复项删除操作直到无法继续删除。 在完成所有重复项删除操作后返回最终的字符串。答案保证唯一。 示例 输入“abbaca” 输出“ca” 解释 例如在 “abbaca” 中我们可以删除 “bb” 由于两字母相邻且相同这是此时唯一可以执行删除操作的重复项。之后我们得到字符串 “aaca”其中又只有 “aa” 可以执行重复项删除操作所以最后的字符串为 “ca”。 提示 1 S.length 20000 S 仅由小写英文字母组成。 class Solution {
public:string removeDuplicates(string s) {// 使用栈stackchar st;for(int i0;is.size();i){if(st.empty()||st.top()!s[i]){st.push(s[i]);}else{st.pop();}}if(st.empty()) return ;string result;while(!st.empty()){result st.top();st.pop();}reverse(result.begin(),result.end());return result;}
};五、逆波兰表达式求值力扣150 给你一个字符串数组 tokens 表示一个根据 逆波兰表示法 表示的算术表达式。 请你计算该表达式。返回一个表示表达式值的整数。 注意 有效的算符为 ‘’、‘-’、’ 和 ‘/’ 。 每个操作数运算对象都可以是一个整数或者另一个表达式。 两个整数之间的除法总是 向零截断 。 表达式中不含除零运算。 输入是一个根据逆波兰表示法表示的算术表达式。 答案及所有中间计算结果可以用 32 位 整数表示。 示例 1 输入tokens [“2”,“1”,“”,“3”,“] 输出9 解释该算式转化为常见的中缀算术表达式为((2 1) * 3) 9 示例 2 输入tokens [“4”,“13”,“5”,”/“,”“] 输出6 解释该算式转化为常见的中缀算术表达式为(4 (13 / 5)) 6 示例 3 输入tokens [“10”,“6”,“9”,“3”,”“,”-11,““,”/“,””,“17”,“”,“5”,“”] 输出22 解释该算式转化为常见的中缀算术表达式为 ((10 * (6 / ((9 3) * -11))) 17) 5 ((10 * (6 / (12 * -11))) 17) 5 ((10 * (6 / -132)) 17) 5 ((10 * 0) 17) 5 (0 17) 5 17 5 22 class Solution {
public:int evalRPN(vectorstring tokens) {//使用栈进行操作stacklong long st;long long result;for(int i0;itokens.size();i){if(tokens[i]||tokens[i]-||tokens[i]*||tokens[i]/){// 是符号// 取出两个进行运算long long num2 st.top();st.pop();long long num1 st.top();st.pop();if(tokens[i]) st.push(num1num2);else if(tokens[i]-) st.push(num1-num2);else if(tokens[i]*) st.push(num1*num2); else st.push(num1/num2);}else{st.push(stoll(tokens[i]));}}int fin st.top();st.pop();return fin;}
};六、滑动窗口最大值力扣239 给你一个整数数组 nums有一个大小为 k 的滑动窗口从数组的最左侧移动到数组的最右侧。你只可以看到在滑动窗口内的 k 个数字。滑动窗口每次只向右移动一位。 返回 滑动窗口中的最大值 。 示例 1 输入nums [1,3,-1,-3,5,3,6,7], k 3 输出[3,3,5,5,6,7] 解释 滑动窗口的位置 最大值 [1 3 -1] -3 5 3 6 7 3 1 [3 -1 -3] 5 3 6 7 3 1 3 [-1 -3 5] 3 6 7 5 1 3 -1 [-3 5 3] 6 7 5 1 3 -1 -3 [5 3 6] 7 6 1 3 -1 -3 5 [3 6 7] 7 示例 2 输入nums [1], k 1 输出[1] 提示 1 nums.length 105 -104 nums[i] 104 1 k nums.length class Solution {// 使用双端队列class Myduque{public:dequeint dq;void mypop(int val){if(!dq.empty()valdq.front()){dq.pop_front();}}void mypush(int val){while(!dq.empty()valdq.back()){dq.pop_back();}// 添加队列dq.push_back(val);}int getMax(){return dq.front();}};
public:vectorint maxSlidingWindow(vectorint nums, int k) {// 定义结果列表vectorint result;Myduque Mydq;// 现将前k个元素添加到队列for(int i0;ik;i){Mydq.mypush(nums[i]);}// 添加结果result.push_back(Mydq.getMax());for(int ik;inums.size();i){// 添加一个Mydq.mypush(nums[i]);// 弹出一个Mydq.mypop(nums[i-k]);// 结果添加到列表result.push_back(Mydq.getMax());}return result;}
};七、前 K 个高频元素力扣347 给你一个整数数组 nums 和一个整数 k 请你返回其中出现频率前 k 高的元素。你可以按 任意顺序 返回答案。 示例 1: 输入: nums [1,1,1,2,2,3], k 2 输出: [1,2] 示例 2: 输入: nums [1], k 1 输出: [1] 提示 1 nums.length 105 k 的取值范围是 [1, 数组中不相同的元素的个数] 题目数据保证答案唯一换句话说数组中前 k 个高频元素的集合是唯一的 进阶你所设计算法的时间复杂度 必须 优于 O(n log n) 其中 n 是数组大小。 class Solution {class Mycompare{public:bool operator()(const pairint,int left,const pairint,int right){return left.secondright.second;}};
public:vectorint topKFrequent(vectorint nums, int k) {// 结果数组vectorint result;// 使用map存储unordered_mapint,int Mymap;// 统计每个元素出现的次数for(int i0;inums.size();i){Mymap[nums[i]];}// for(unordered_mapint,int::iterator itMymap.begin();it!Mymap.end();it){// cout(*it).first:(*it).secondendl;// }// 使用小顶堆筛选出出现次数最多的k个priority_queuepairint,int,vectorpairint,int,Mycompare smallQueue;// 遍历map添加到优先队列中for(unordered_mapint,int::iterator itMymap.begin();it!Mymap.end();it){smallQueue.push(*it);if(smallQueue.size()k){smallQueue.pop();}}// 获取最终的结果while(!smallQueue.empty()){result.push_back(smallQueue.top().first);smallQueue.pop();}return result;}
};