首页 > 开发 > PHP > 正文

php四则运算:中缀表达式转后缀表达式例子

2024-05-04 21:59:58
字体:大 中 小
来源:转载
供稿:网友

很多人对于四则运算可能不太明天了,下面我们来看看关于php四则运算,中缀表达式转后缀表达式例子,有需要了解的朋友可以一起来看看吧.

四则运算表达式,我们书面使用的叫做中缀表达式,而计算器,却更加喜欢后缀表达,括号优先级,加减乘除优先级等使得运算中缀四则表达式变得困难,这个时候引入了一种计算机喜欢的格式,叫做后缀表达式,本文以PHP代码,实现中缀表达式转后缀表达式的逻辑.

本文以PHP为代码环境,有人会说高级语言直接写表达式就好了,它们会算,可是他们为什么会算,怎么算的,还是需要把中缀表达式转为后缀表达式,因此本文代码只是模拟一个逻辑.

比如:传统的四则运算表达式(中缀表达式)是9 + ( 3 - 1 ) * 3 + 10 / 2,对应的后缀表达式就是9 3 1 - 3 * + 10 2 / +。

转换逻辑:一个字符一个字符的输入,如果是数字则直接输出,如果是左括号则直接入栈,如果是右括号则开始出栈,直到遇到第一次左括号为止,如果是加减乘除,则判断,如果栈顶也是符号,且输入的符号的优先级不高于栈顶的符号优先级,则全部出栈,否则该输入的符号入栈.

  1. <?php 
  2. /** 
  3.  * 将输入的字符按照中缀表达式转后缀表达式的规则处理 
  4.  * @param $str 输入的字符 
  5.  * @param $stack 栈 
  6.  * @param $newStrList 新的表达式 
  7.  */ 
  8. function suffix($str, &$stack, &$newStrList){ 
  9.     //如果是数字则输出 
  10.     if(is_numeric($str)){ 
  11.         $newStrList .= $str . ' '; 
  12.     } 
  13.     //如果是左括号则入栈 
  14.     else if($str == '('){ 
  15.         $stack[] = $str; 
  16.     } 
  17.     //如果是右括号则将最近的左括号之前的所有数据出栈 
  18.     else if($str == ')'){ 
  19.         while($arrPop = array_pop($stack)){ 
  20.             if($arrPop == '('){ 
  21.                 break; 
  22.             } 
  23.             $newStrList .= $arrPop . ' '; 
  24.         } //开源软件:Vevb.com 
  25.     } 
  26.     //如果是加减乘除则判断与栈顶符号优先级 
  27.     else if(in_array($str, array('+', '-', '*', '/')) && count($stack) > 0){ 
  28.         $key  = (count($stack) - 1); 
  29.         if(in_array($stack[$key], array('+', '-', '*', '/'))){ 
  30.             //该符号优先级不高于栈顶符号的 
  31.             if(checkPriority($str, $stack[$key]) != 1){ 
  32.                 for($i=$key; $i>=0; $i--){ 
  33.                     if($stack[$i] == '('){ 
  34.                         break; 
  35.                     } 
  36.                     $newStrList .= $stack[$i] . ' '; 
  37.                     unset($stack[$i]); 
  38.                     $stack = array_values($stack); 
  39.                 } 
  40.             } 
  41.         } 
  42.         //本次的符号入栈 
  43.         $stack[] = $str; 
  44.     }else{ 
  45.         $stack[] = $str; 
  46.     } 
  47. } 
  48.  
  49. /** 
  50.  * 判断运算符的优先级 
  51.  * @param $operatorA 
  52.  * @param $operatorB 
  53.  * @return A大于B返回1,A等于B返回0,A小于B返回-1 
  54.  */ 
  55. function checkPriority($operatorA, $operatorB){ 
  56.     switch($operatorA){ 
  57.         case '+': 
  58.         case '-': 
  59.             if($operatorB == '+' || $operatorB == '-'){ 
  60.                 return 0; 
  61.             }else if($operatorB == '*' || $operatorB == '/'){ 
  62.                 return -1; 
  63.             } 
  64.             break; 
  65.         case '*': 
  66.         case '/': 
  67.             if($operatorB == '+' || $operatorB == '-'){ 
  68.                 return 1; 
  69.             }else if($operatorB == '*' || $operatorB == '/'){ 
  70.                 return 0; 
  71.             } 
  72.             break; 
  73.         default: 
  74.             exit('error'); 
  75.     } 
  76. } 
  77. //栈 
  78. $stack = array(); 
  79. //待转换的表达式 
  80. $strList = '9 + ( 3 - 1 ) * 3 + 10 / 2'; 
  81. //新的表达式 
  82. $newStrList = ''; 
  83. $strList = explode(' ', $strList); 
  84. foreach($strList as $str){ 
  85.     if($str != ' '){ 
  86.         suffix($str, $stack, $newStrList); 
  87.     } 
  88. } 
  89. //数组反转 
  90. while($s = array_pop($stack)){ 
  91.     $newStrList .= $s . ' '; 
  92. } 
  93. echo $newStrList; 
  94. ?>

发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表