Advertisement
HwapX

Math Solver - Shunting Yard v2

Oct 29th, 2015
94
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. <?php
  2.  
  3. function tokenize($expr) {
  4.     preg_match_all('/(?:-|)\d+|\+|-|\*|\^|\/|\(|\)/', $expr, $match);
  5.     $match  = $match[0];
  6.     $tokens = array();
  7.     $stack  = array();
  8.     $precedence = array('+' => 2, '-' => 2, '*' => 3, '/' => 3, '^' => 4);
  9.    
  10.     while($match) {
  11.         $token = array_shift($match);
  12.        
  13.         if(is_numeric($token)) {
  14.             array_push($tokens, $token);
  15.             continue;
  16.         }
  17.        
  18.         if($token === ')') {
  19.             while($stack && end($stack) !== '(') {
  20.                 array_push($tokens, array_pop($stack));
  21.             }
  22.            
  23.             array_pop($stack);
  24.             continue;
  25.         }
  26.        
  27.         while($token !== '(' && ($stack && end($stack) !== '(') && $precedence[$token] < $precedence[end($stack)]) {
  28.             array_push($tokens, array_pop($stack));
  29.         }
  30.        
  31.         array_push($stack, $token);
  32.     }
  33.    
  34.     return array_merge($tokens, array_reverse($stack));
  35. }
  36.  
  37. function resolve($math) {  
  38.     $funcs = array(
  39.         '+' => function ($left, $right) { return $left + $right; },
  40.         '-' => function ($left, $right) { return $left - $right; },
  41.         '/' => function ($left, $right) { return $left / $right; },
  42.         '*' => function ($left, $right) { return $left * $right; },
  43.         '^' => 'pow'
  44.     );
  45.    
  46.     $stack = array();
  47.    
  48.     while(count($math) > 1) {
  49.         $token = array_shift($math);
  50.        
  51.         if(!is_numeric($token)) {
  52.             $token = $funcs[$token](array_shift($math), array_shift($math));
  53.         }
  54.        
  55.         array_push($stack, $token);
  56.     }
  57.    
  58.     return $stack[0];
  59. }
  60.  
  61. header('content-type: text/plain');
  62. $math = tokenize('3 + 4 * 2 / ( 1 - 5 ) ^ 2 ^ 3');
  63. echo implode(' ', $math) . PHP_EOL;
  64. echo resolve($math);
  65.  
  66. ?>
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement