当前位置: 首页 > news >正文

LeetCode - 227. 基本计算器 II

问题

227. 基本计算器 II - 力扣(LeetCode)

思路

这道题我会用栈来解决,具体思路是:

  1. 使用一个栈来存储数字
  2. 用一个变量记录当前的运算符,初始为'+'
  3. 用一个变量记录当前处理的数字

然后从左到右扫描表达式,处理过程如下:

  1. 我们不是立即计算表达式,而是根据运算符的优先级延迟计算
  2. 对于加减法,我们先把数字压入栈(减法就压入负数)
  3. 对于乘除法,我们立即与栈顶元素计算,然后将结果压回栈中
  4. 最后,栈中所有数字相加就是最终结果

这种方法很巧妙地处理了运算符优先级问题,不需要显式比较优先级。

使用单栈+操作符方法处理表达式 '3+5 / 2' 的过程:

初始状态:

  • 数字栈:空
  • 当前操作符:'+'(默认初始值)
  • 当前数字:0

扫描到字符 '3':

  • 更新当前数字:num = 3

扫描到字符 '+':

  • 根据当前操作符'+' 处理数字3:将3压入栈,栈变为 [3]
  • 更新当前操作符:op = '+'
  • 重置当前数字:num = 0

扫描到字符 '5':

  • 更新当前数字:num = 5

扫描到字符 '/':

  • 根据当前操作符'+' 处理数字5:将5压入栈,栈变为 [3, 5]
  • 更新当前操作符:op = '/'
  • 重置当前数字:num = 0

扫描到字符 '2':

  • 更新当前数字:num = 2

到达字符串末尾:

  • 根据当前操作符'/' 处理数字2:
  • 从栈中弹出顶部元素5
  • 计算 5 / 2 = 2(整数除法)
  • 将结果2压回栈中,栈变为 [3, 2]

计算最终结果:

  • 将栈中所有元素相加:3 + 2 = 5
  • 返回结果5

需要注意的几个点:

  1. 处理多位数字,因为表达式中的数字可能不只是单个数字,使用while循环
  2. 处理空格,需要跳过

这个算法的时间复杂度是O(n),其中n是字符串的长度,因为我们只需要遍历一次字符串。空间复杂度是O(n),最坏情况下栈可能需要存储所有数字。

读者可能出现的情况

class Solution {
public:int calculate(string s) {stack<int> st;char op = '+';int i = 0;while(i < s.size()){if(s[i] == ' '){i++;}else if(s[i] >= '0' && s[i] <= '9'){int num = 0;while(s[i] >= '0' && s[i] <= '9'){num = num * 10 + (s[i] - '0');i++;}if(op == '+'){st.push(num);}else if(op == '-'){st.push(-num);}else if(op == '*'){int top = st.top();st.pop();st.push(num * top);}else{int top = st.top();st.pop();st.push(num / top);}}else{op = s[i];i++;}}int ret = 0;while(st.size()){ret+=st.top();st.pop();}return ret;}
};

在这段代码中,你将当前读取的数字num作为第一个操作数,将栈顶元素top作为第二个操作数。但实际上,栈顶元素是之前处理的数字,应该是第一个操作数。

例如,对于表达式 "5*2",你的代码会计算 2*5,这虽然结果相同,但对于除法就会出问题。对于 "6/2",你的代码会计算 2/6=0,而正确结果应该是 6/2=3。

正确写法

class Solution {
public:int calculate(string s) {stack<int> st;char op = '+';int i = 0;while(i < s.size()){if(s[i] == ' '){i++;}else if(s[i] >= '0' && s[i] <= '9'){int num = 0;while(s[i] >= '0' && s[i] <= '9'){num = num * 10 + (s[i] - '0');i++;}if(op == '+'){st.push(num);}else if(op == '-'){st.push(-num);}else if(op == '*'){int top = st.top();st.pop();st.push(top * num);}else{int top = st.top();st.pop();st.push(top / num);}}else{op = s[i];i++;}}int ret = 0;while(st.size()){ret+=st.top();st.pop();}return ret;}
};
http://www.dtcms.com/a/352443.html

相关文章:

  • C++ `std::map` 解析:`find`, `end`, `insert` 和 `operator[]`
  • redis 在 nodejs 中如何应用?
  • 常用 Kubernetes (K8s) 命令指南
  • DevSecOps 集成 CI/CD Pipeline:实用指南
  • 【RAGFlow代码详解-30】构建系统和 CI/CD
  • 【智能化解决方案】大模型智能推荐选型系统方案设计
  • 简明 | ResNet特点、残差模块、残差映射理解摘要
  • VGVLP思路探索和讨论
  • C++ 并发编程中的锁:总结与实践
  • 绝命毒师模拟器2|单机+联机+绝命毒师模拟器1 全DLC(Drug Dealer Simulator 2+1)免安装中文版
  • 事件驱动架构详解
  • AI Agent安全的“阿喀琉斯之踵”:深度解析MCP核心风险与纵深防御架构
  • Python爬虫: 分布式爬虫架构讲解及实现
  • mysql是怎样运行的(梳理)
  • Java基础第二课:hello word
  • 传统联邦 VS 联邦+大模型
  • freeModbus TCP收发数据一段时间后,出现掉线情况(time out问题)
  • 依托边缘计算方案,移动云全面化解算力、效率、安全平衡难题
  • Wireshark捕获数据的四种层次
  • 【Python数据分析】商品数据可视化大屏项目
  • YggJS RButton 按钮组件 v1.0.0 使用教程
  • 亚马逊运营效能提升:广告策略优化与自配送售后管理的协同路径
  • Makefile构建优化:提升编译效率的关键
  • 打卡day49
  • RocketMq程序动态创建Topic
  • 在 Ubuntu 下遇到 <string>头文件找不到的问题
  • 运筹优化(OR)-在机器学习(ML)浪潮中何去何从?
  • 独孤思维:无限分发,无成本赚钱的副业
  • JVM分层编译深度解析:完整机制与实践指南
  • 面向世界模型构建的跨模态认知网络工程