c++实现简单eval
来源:互联网 发布:河北网络干部学院 编辑:程序博客网 时间:2024/05/29 19:26
题目链接:2017 计蒜之道 初赛 第二场——百度的科学计算器(简单)
给定一个合法的字符串(可以含有整数、小数、加号、减号、括号)的字符串,计算其值
// 将s分隔成多个整体(整数、小数、运算符、括号中的部分均算作一个整体)std::vector<std::string> split(const std::string& s) { std::vector<std::string> ret; if (s.length() == 0) return ret; // bracket if (s.at(0) == '(') { int cnt = 0; for (int i = 0; i < s.length(); i++) { if (s.at(i) == '(') cnt++; else if (s.at(i) == ')') cnt--; if (cnt == 0) { ret.push_back(s.substr(0, i + 1)); auto r = split(s.substr(i + 1)); std::copy(r.begin(), r.end(), std::back_inserter(ret)); break; } } } // number else if (('0' <= s.at(0) && s.at(0) <= '9') || s.at(0) == '.') { ret.push_back(""); for (int i = 0; i < s.length(); i++) { if (('0' <= s.at(i) && s.at(i) <= '9') || s.at(i) == '.') ret.back() += s.at(i); else { auto r = split(s.substr(i)); std::copy(r.begin(), r.end(), std::back_inserter(ret)); break; } } } // operator else { ret.push_back(s.substr(0, 1)); auto r = split(s.substr(1)); std::copy(r.begin(), r.end(), std::back_inserter(ret)); } return ret;}// 支持s中含有括号、小数、整数、加号、减号double calc(std::string s) { auto parts = split(s); if (parts.size() == 0) return 0; if (parts.size() == 1) { // 如果给定字符串是括号括起来的表达式 if (s.at(0) == '(') return calc(s.substr(1, s.length() - 2)); else { assert(('0' <= s.at(0) && s.at(0) <= '9') || s.at(0) == '.'); // stod函数是c++11标准支持的,需要编译器不能太老 return std::stod(s); } } double ret = calc(parts.at(0)); for (int i = 1; i < parts.size(); i += 2) { assert(i + 1 < parts.size()); if (parts.at(i) == "+") ret += calc(parts.at(i + 1)); else if (parts.at(i) == "-") ret -= calc(parts.at(i + 1)); else assert(false); } return ret;}int main(int argc, char *argv[]) { int n; std::cin >> n; std::string s; std::cin >> s; double ans = calc(s); if (s.find(".") == std::string::npos) std::cout << (long long)ans << std::endl; else printf("%.6f\n", ans); return 0;}
另一种比较好的写法,修改自这个blog
这段代码主要思路是:建立表达式树
template<class T>class Calc { static const int MX = 100000; char op[MX]; int lch[MX], rch[MX], r = 0; T s[MX]; bool DIV_ZERO; int _build(const std::string& S, int L, int R) { int u; int t = L; while (t <= R && (isdigit(S.at(t)) || S.at(t) == '.')) t++; if (t == R + 1) { u = r++; op[u] = '.'; lch[u] = rch[u] = -1; s[u] = std::stod(S.substr(L, t - L)); return u; } std::vector<int> c = { -1, -1 }; for (int i = L, p = 0; i <= R; i++) { if (S.at(i) == '(') p++; else if (S.at(i) == ')') p--; else if ((S.at(i) == '+' || S.at(i) == '-') && !p) c.at(0) = i; else if ((S.at(i) == '*' || S.at(i) == '/') && !p) c.at(1) = i; } if (c.at(0) < 0) c.at(0) = c.at(1); if (c.at(0) < 0) u = _build(S, L + 1, R - 1); else { u = r++; op[u] = S[c[0]]; lch[u] = _build(S, L, c[0] - 1); rch[u] = _build(S, c[0] + 1, R); s[u] = -1; } return u; } T _calc(int u) { if (op[u] == '.') return s[u]; T al = _calc(lch[u]), ar = _calc(rch[u]); switch (op[u]) { case '+': return al + ar; case '-': return al - ar; case '*': return al * ar; case '/': return (ar == 0 ? DIV_ZERO = 1 : al / ar); } assert(false); return al; }public: T solve(const std::string& s) { r = 0; DIV_ZERO = false; int u = _build(s, 0, (int)s.length() - 1); if (!DIV_ZERO) return _calc(u); else /// 运算过程中发生除0 return INF; }};Calc<long long> int_calc;Calc<long double> dbl_calc;int main() { int n; while (std::cin >> n) { std::string expr; std::cin >> expr; if (expr.find(".") == std::string::npos) { long long ans = int_calc.solve(expr); printf("%lld\n", ans); } else { long double ans = dbl_calc.solve(expr); printf("%.6f\n", (double)ans); } } return 0;}
阅读全文
1 0
- c++实现简单eval
- 实现一个简单的 eval 函数计算加减法和括号
- eval简单用法
- 简单说 eval( )函数
- as3 eval实现
- 全局eval的实现
- 简单计算器实现(C++)
- c++vector简单实现
- C实现简单列表
- javascript eval的简单用法
- java 实现 js eval功能
- 简单五子棋----C语言实现
- C语言实现简单单链表
- linux c实现简单shell
- C语言简单实现五子棋
- C实现简单循环队列
- ANTLR实现简单计算器[C#]
- c循环队列简单实现
- Linux系统操作(3)———JDK、eclipse、Tomcat的安装
- 1118. Birds in Forest (25)[并查集]
- ViewFlipper
- (DP)LeetCode#53. Maximum Subarray
- 浏览器中调试js代码
- c++实现简单eval
- QDU首届易途杯大赛-ycb老师与一道简单的物理题
- LeetCode 21. Merge Two Sorted Lists(链表)
- c单链表
- Jquery高级编程(一)
- c语言基础-流程控制06
- https 代理
- MarkdownPad2的一些设置与用法【持续更新······】
- 人工智能之产生式系统