微信小程序计算算术表达式(代替JS中的eval函数)
2018-03-16 14:01
225 查看
小程序中计算算术表达式
大家都知道 JS 中的 eval 函数可以直接计算出算术表达式的结果(当然它还有更多的实用策略),但是到了微信小程序,把这个函数给割了,所以,折腾无果后,自己写了个,仅供大家参考。前情提要:
- 微信小程序中 eval 函数被割; - 网上未找到合适的工具类(尝试用了 rpn.js ,括号嵌套时结果不太满意)。
声明:
- 本文提及的内容均为原创,难免有不规范或不合理的地方,各位海涵。 - 文中所述方案,仅以满足自身需求为目的,所以考虑的不是特别全面,后续完善下。 - 关于JS闭包等操作,此处不涉及,各位看官自行处理;
先说下逻辑:
比如需要计算一个算式是否等于24,这个过程中,算式是字符串拼出来的,是否等于24的关键就是先得出算式的计算结果,比如计算 ‘(13-5)*(9-6)’ :- 1、传入算式前,确保算式格式正确(因为计算内部没有做严谨的判断); - 2、优先计算括号内的内容(判断括号内的内容,建议从第一个右括号开始,向前查询最近的一个左括号,这样循环下来,即可保证括号优先计算正常); - 3、计算加减乘除(去括号后,先计算乘除,后计算加减)。 - 4、其他语言可以参考此思路,自行处理。
遇到的坑
本人JS菜鸟,写这个时候爬坑N多,略记一二。 - 从字符串中提取的数字,做加法计算的时候,需要把字符转成数字,否则会出现‘1’+‘1’ = ‘11’的情况; - 修改变量名,一定要及时把所有引用的地方都修改好,否则就没有否则了... - 网上的代码,下下来一定要仔细测试,包括我的代码。
上代码
/** * By Chice * Date:20180316 * 2206143885@qq.com */ /**计算没有括号的表达式的值(操作符限定为'+'、'-'、'*'、'/') */ function calcExpressionWithoutQuote(expression) { if ((expression.indexOf('(') > -1) || (expression.indexOf(')') > -1)) { return calcQuote(expression); } var operators = []; var nums = []; var lastOperatorIndex = -1; for (var i = 0; i < expression.length; i++) { var charAtIndex = expression.charAt(i); if (isOperatorChar(charAtIndex)) { operators[operators.length] = charAtIndex; nums[nums.length] = expression.substring(lastOperatorIndex + 1, i); lastOperatorIndex = i; } if (i == (expression.length - 1) && lastOperatorIndex < i) { nums[nums.length] = expression.substring(lastOperatorIndex + 1, expression.length); } } if (operators.length <= 0 || nums.length <= 0) { return expression; } while (operators.indexOf('*') > -1 || operators.indexOf('/') > -1) { operators.forEach(function (value, index) { if (value == '*' || value == '/') { // 拿到操作符位置。 var tempResult = calcExpressionWithSingleOperator(nums[index], nums[index + 1], value); operators.splice(index, 1); nums.splice(index, 2, [tempResult]); } }); } var calcResult = nums[0] * 1; // 现在只剩下'+'、'-'了 if (operators.indexOf('+') > -1 || operators.indexOf('-') > -1) { for (var index = 0; index < operators.length; index++) { var value = operators[index]; if (value == '+' || value == '-') { calcResult = calcExpressionWithSingleOperator(calcResult, nums[index + 1], value); } } return calcResult; } else { return (nums[0] * 1); } } /** * 计算只有一个操作符的表达式的值(操作符限定为'+'、'-'、'*'、'/') */ function calcExpressionWithSingleOperator(num1, num2, operator) { if (operator == '+') return num1 * 1 + num2 * 1; if (operator == '-') return num1 * 1 - num2 * 1; if (operator == '*') return num1 * num2; if (operator == '/') return num1 / num2; return NaN; } /** 计算算术表达式的值 */ function calcExpression(expression) { expression = expression.replace(/\s/g, '').replace(/÷/g, '/').replace(/x/g, '*').replace(/×/g, '*').replace(/X/g, '*'); if (getCharCountInString(expression, '(') != getCharCountInString(expression, ')')) return NaN; while (expression && (expression.indexOf('(') > -1) && (expression.indexOf(')') > -1)) { var firstRightQuoteIndex = expression.indexOf(')'); var leftQuoteIndex = expression.indexOf('('); for (var i = leftQuoteIndex; i < firstRightQuoteIndex; i++) { if (expression.charAt(i) == '(') { leftQuoteIndex = i; } } var tempExpression = expression.substring(leftQuoteIndex + 1, firstRightQuoteIndex); var tempValue = calcExpressionWithoutQuote(tempExpression); expression = expression.substring(0, leftQuoteIndex) + tempValue + expression.substring(firstRightQuoteIndex + 1, expression.length); } return calcExpressionWithoutQuote(expression); } /**获取字符串中某子字符串出现次数 */ function getCharCountInString(strings, chars) { return (strings.split(chars)).length - 1; } /**判断字符是否是运算符 */ function isOperatorChar(aimChar) { return '+-*/'.indexOf(aimChar) > - 1; } module.exports = { //导出函数,供需求处调用 calcExpression: calcExpression }
a347
相关文章推荐
- 微信小程序使用第三方库(第三方js)问题
- 微信小程序 Node.js (基础十) 路由
- 微信小程序 - app.js文件
- 微信小程序中JS对象属性赋值
- JS中微信小程序自定义底部弹出框
- 微信小程序 - WapRequest.js
- 微信小程序之计算时间差
- 微信小程序--亲戚称呼计算
- 微信小程序 JS动态修改样式
- 微信小程序使用三元运算符代替wx:if
- 基于Node.js+MySQL开发的开源微信小程序B2C商城(页面高仿网易严选)
- 微信小程序 image组件binderror使用例子与js中的onerror区别
- 微信小程序WeUI.js网页开发样式库
- 微信小程序 js逻辑
- 微信小程序 Node.js (基础十一) 全局对象
- "口令红包"-利用函数计算构建微信小程序的server端
- 微信小程序 Node.js (基础七) Stream(流)
- js 替换掉 Emoji 微信小程序
- 微信小程序 + mock.js 实现后台模拟及调试
- Ubuntu 16.04 下部署Node.js+MySQL微信小程序商城