PHP逆波兰表达式的算法
2
3 关于PHP计算工资问题。以下一篇文章中谈到一种计算工资的方法,称作逆波兰的算法。
4
5 我们的目标是实现如下的计算公式:
6
7 假设有一个计算公式如下:
8
9 $expression = "(F1*F12+10.34) ";
10
11 其中的变量值如下:
12
13 $expression_value = Array( 'F1 '=> 10, 'F12 '=> 20);
14
15 我们希望用PHP构建一个类来计算出这个表达式的值。这种应用主要用于web工资管理中,用户可以自定义其工资相公式的情况
16
17 $rpn = new Math_Rpn();
18 $rpn-> setExpressionValue($expression_value);
19 echo $rpn-> calculate($expression, 'deg ',false); // 即为相应的值
20
21 解析逆波兰表达式的方法,编译原理中有,就是先把表达式分解成符号数组,然后求逆波兰式,最后根据逆波兰式得到其结果。
22
23 我分别把三个函数贴在下面,其实本质我就是对Pear的RPN函数进行了Hack.
24
25 function _stringToArray () {
26 $temp_operator = null;
27 $temp_value = null;
28
29 $this-> _input = str_replace( " ", " ",$this-> _input);
30
31 for($i = 0; $i < strlen($this-> _input); $i++) {
32 if ($this-> _input[$i] == ' ') {
33 if ($temp_operator != null) {
34 array_push($this-> _input_array, $temp_operator);
35 $temp_operator = null;
36 }
37 if ($temp_value != null) {
38 array_push($this-> _input_array, $temp_value);
39 $temp_value = null;
40 }
41 } elseif (($temp_value == null) && $temp_operator != ') ' && (!array_key_exists($temp_operator,$this-> _operation) || !array_key_exists(2,$this-> _operation[$temp_operator]) || $this-> _operation[$temp_operator][2]> 0) && ($this-> _input[$i] == '- ')) {
42 if ($temp_operator != null) {
43 array_push($this-> _input_array, $temp_operator);
44 $temp_operator = null;
45 }
46
47 array_push($this-> _input_array, '-1 ');
48 array_push($this-> _input_array, '* ');
49 //} elseif ((is_numeric($this-> _input[$i])) || ($this-> _input[$i] == '. ')) {
50 } elseif ((is_numeric($this-> _input[$i])) || ($this-> _input[$i] == '. ') || ($this-> _input[$i] == 'F ')) {
51 if ($temp_operator != null) {
52 array_push($this-> _input_array, $temp_operator);
53 $temp_operator = null;
54 }
55
56 $temp_value .= $this-> _input[$i];
57 } else {
58 if ($this-> _keyExists($temp_operator, $this-> _operation, 1)) {
59 array_push($this-> _input_array, $temp_operator);
60 $temp_operator = null;
61 }
62
63 if ($temp_value != null) {
64 array_push($this-> _input_array, $temp_value);
65 $temp_value = null;
66 }
67
68 $temp_operator .= $this-> _input[$i];
69 }
70 }
71
72 if ($temp_operator != null && $temp_operator != ' ') {
73 array_push($this-> _input_array, $temp_operator);
74 } elseif($temp_value != null && $temp_value != ' ') {
75 array_push($this-> _input_array, $temp_value);
76 }
77
78 // $this-> _testInput();
79 print_r($this-> _expression_value);
80 print_r($this-> _input_array);
81 return $this-> _input_array;
82 }
83
84 function _arrayToRpn() {
85
86 if ($this-> _error <> null) {
87 $this-> _output = array();
88 return $this-> _output;
89 }
90
91 for($i = 0; $i < count($this-> _input_array); $i++) {
92
93 $temp = $this-> _input_array[$i];
94
95 if (is_numeric($temp)) {
96 $this-> _outputAdd($temp);
97 } else if($this-> _keyExists($temp, $this-> _expression_value, 0)) {
98 $this-> _outputAdd($this-> _expression_value[$temp]);
99 } else {
100 if ($temp == ') ') {
101 while(!$this-> _stackEmpty() && ($this-> _stackPriority() > = 1)) {
102 $this-> _outputAdd($this-> _stackDelete());
103 }
104 if (!$this-> _stackEmpty()) {
105 $this-> _stackDelete();
106 }
107
108 } elseif ($temp== '( ') {
109 $this-> _stackAdd($temp);
110 } elseif (($this-> _stackEmpty()) || (($this-> _priority($temp) > $this-> _stackPriority()))) {
111 $this-> _stackAdd($temp);
112 } else {
113 while(!$this-> _stackEmpty() && ($this-> _priority($temp) <= $this-> _stackPriority())) {
114 $this-> _outputAdd($this-> _stackDelete());
115 }
116 $this-> _stackAdd($temp);
117 }
118
119 }
120
121 }
122
123 while(!$this-> _stackEmpty()) {
124 $this-> _outputAdd($this-> _stackDelete());
125 }
126
127 return $this-> _output;
128 }
129
130 function _rpnToValue() {
131
132 $time1 = $this-> _getMicroTime();
133
134 if ($this-> _error <> null) {
135 $this-> _value = null;
136 return $this-> _value;
137 }
138
139 $this-> _value = 0;
140 $temp = $this-> _output;
141
142 do {
143 $pos = $this-> _nextOperator($temp);
144
145 if ($pos == -1) {
146 $this-> _error = $this-> _raiseError( 'Syntax error ');
147 $this-> _value = null;
148 return $this-> _value;
149 }
150
151 $operator = $this-> _operation[$temp[$pos]];
152 $arg = $operator[2];
153 $function = $operator[3];
154
155 if (($arg==2) && (!isset($temp[$pos-1]) || !is_numeric($temp[$pos-1]) || !isset($temp[$pos-2]) || !is_numeric($temp[$pos-2]))) {
156 $this-> _error = $this-> _raiseError( 'Syntax error ');
157 $this-> _value = null;
158 return $this-> _value;
159 } elseif (($arg==1) && (!isset($temp[$pos-1]) || !is_numeric($temp[$pos-1]))) {
160 $this-> _error = $this-> _raiseError( 'Syntax error ');
161 $this-> _value = null;
162 return $this-> _value;
163 }
164
165 if(is_array($function)) {
166
167 if($arg==2) $arg_array = array($temp[$pos-2],$temp[$pos-1]);
168 elseif($arg==1) $arg_array = array($temp[$pos-1]);
169 else $arg_array = array();
170
171 if($function[ 'type '] == 'userFunction ') {
172 $this-> _value = call_user_func_array($function[ 'function '], $arg_array);
173 } else {
174 $function_array = array(&$function[ 'class '], $function[ 'method ']);
175 $this-> _value = call_user_func_array($function_array, $arg_array);
176 }
177 } else {
178 $this-> _value = $this-> $function($temp, $pos);
179 }
180
181 if ($this-> _isNan($this-> _value)) {
182 $this-> _error = $this-> _raiseError( 'NAN value ');
183 $this-> _value = null;
184 return $this-> _value;
185 } elseif ($this-> _isInfinite($this-> _value)) {
186 $this-> _error = $this-> _raiseError( 'Infinite value ');
187 $this-> _value = null;
188 return $this-> _value;
189 } elseif (is_null($this-> _value)) {
190 return $this-> _value;
191 }
192
193 $temp = $this-> _refresh($temp, $pos, $arg, $this-> _value);
194 } while(count($temp) > 1);
195
196 $this-> _value = $temp[0];
197
198 $time2 = $this-> _getMicroTime();
199
200 $this-> _timer = $time2 - $time1;
201
202 return $this-> _value;
203 }
204
转载于:https://www.cnblogs.com/voswin/articles/1497291.html
PHP逆波兰表达式的算法相关推荐
- nyoj35——逆波兰表达式
逆波兰表达式又称作后缀表达式,在四则混合运算的程序设计中用到. 例如: 1+2写成后缀表达式就是12+ 4+5*(3-2)的后缀表达式就是4532-*+ 后缀表达式在四则运算中带来了意想不到的方便,在 ...
- java 实现逆波兰表达式_逆波兰表达式java实现
知道逆波兰表达式是一个偶然的情况,在用js的时候偶然发现了js中的一个eval函数,数学的表达式它竟然能直接解析出结果.后面通过查询才得知里面的核心是用的逆波兰表达式的算法.后面网上找了一下java的 ...
- JavaScript逆波兰表达式求值
逆波兰表达式简介 逆波兰表达式又叫做后缀表达式.逆波兰表示法是波兰逻辑学家J・卢卡西维兹(J・ Lukasiewicz)于1929年首先提出的一种表达式的表示方法 .后来,人们就把用这种表示法写出的表 ...
- Algorithm:C++语言实现之链表相关算法(单链公共结点问题、一般LCA、括号匹配、最长括号匹配、逆波兰表达式Reverse Polish Notation、直方图矩形面积、收集雨水问题)
Algorithm:C++语言实现之链表相关算法(单链公共结点问题.一般LCA.括号匹配.最长括号匹配.逆波兰表达式Reverse Polish Notation.直方图矩形面积.收集雨水问题) 目录 ...
- 调度场算法与逆波兰表达式
本文的主要内容是如何求一个给定的表达式的值,具体思路就是先将普通算术的中缀表达式转化为后缀表达式,这一步用到的算法叫做调度场算法.然后对后缀表达式,也就是逆波兰表达式求值. 题目:http://acm ...
- 逆波兰计算器android源码简书,计算器的核心算法-JavaScript实现(逆波兰表达式)...
最终计算器的掩饰效果,欢迎大家来找BUG. http://codepen.io/lvanboy/full/LxKVxJ/ 功能: 1.按照运算符的优先级运算 2.利用上次的结果继续运算 3.多个数字混 ...
- (补)算法训练Day13 | LeetCode150. 逆波兰表达式求值(栈应用);LeetCode239. 滑动窗口最大值(单调队列);LeetCode347. 前K个高频元素(小顶堆,优先级队列)
目录 LeetCode150. 逆波兰表达式求值 1. 思路 2. 代码实现 3. 复杂度分析 4. 思考 LeetCode239. 滑动窗口最大值 1. 思路 2. 代码实现 3. 复杂度分析 4. ...
- 设计一个算法,将一般算术表达式转化为逆波兰表达式,并求逆波兰表达式的值
栈的设计与使用 实验内容 设计一个算法,将一般算术表达式转化为逆波兰表达式,并求逆波兰表达的值 解题思路 (1)一般算术表达(中缀表达),如#3×(4+2)/2-5#,#为表达式界定符,逆波兰表达式( ...
- 【数据结构与算法】之深入解析“逆波兰表达式求值”的求解思路与算法示例
一.题目要求 根据逆波兰表示法,求表达式的值.有效的算符包括 +.-.*./,每个运算对象可以是整数,也可以是另一个逆波兰表达式. 两个整数之间的除法只保留整数部分. 可以保证给定的逆波兰表达式总是有 ...
- 算法训练Day11|LeetCode 20. 有效的括号、1047. 删除字符串中的所有相邻重复项、150. 逆波兰表达式求值
题目链接:20. 有效的括号 第一种情况:已经遍历完了字符串,但是栈不为空,说明有相应的左括号没有右括号来匹配,所以return false 第二种情况:遍历字符串匹配的过程中,发现栈里没有要匹配的字 ...
最新文章
- JSP学习笔记(四十九):抛弃POI,使用iText生成Word文档
- python--numpy pad函数使用
- vb 设置打印机 任意尺寸_打印照片怎么设置尺寸
- 编码不一致问题-Illegal mix of collations
- jQuery 元素操作——遍历元素
- C语言实现heap sort堆排序的算法(附完整源码)
- Golang 常见设计模式之装饰模式
- jsp中去掉超链接下划线吗_好烦啊,PPT 插入超链接,文字自动变色还有下划线!还不能改?!...
- mysql 数据库 应用_MySQL数据库的应用
- 计算不定方程解的个数的方法汇总
- 08-04 性能测试--复杂情景设计
- Nginx 架构原理
- 网站扫码登录时怎么一回事?
- Qt 识别 DM 码
- win7如何安装IIS,三种方法任你选(图文教程)
- 计算机毕业设计Java医院医患管理系统(系统+源码+mysql数据库+Lw文档)
- UI 即 User Interface( 用户界面 ) 的简称
- ISTQB基础级考试心得
- 微信图片翻译技术优化之路
- python pyecharts 画图 饼图柱状图
热门文章
- Pointer is missing a nullability type specifier (__nonnull or __nullable)
- 书------编程书(FoxPro)
- Visual Studio Code如何打开多个tab标签
- Luogu2665[USACO08FEB] 连线游戏
- stringbuffer java API_java API中Object,String,Stringbuffer,StringBuilder的总结
- python语言程序设计期末试卷_Python语言程序设计17182试题题目及答案,课程2020最新期末考试题库,章节测验答案...
- 动态代理和静态代理的区别_动态代理与静态代理
- 酷狗php 技术题目,广州酷狗php面试题(赋答案)
- nginx 文件服务器_Nginx必不可少啊!!!
- redis常用命令与常用api