1.20.x evalmath.inc EvalMath::evaluate($expr)

File

includes/evalmath.inc, line 112

Class

EvalMath

Code

function evaluate($expr) {
  $this->last_error = null;
  $expr = trim($expr);
  if (substr($expr, -1, 1) == ';') {
    $expr = substr($expr, 0, strlen($expr) -1); // strip semicolons at the end
  }
  //===============
  // is it a variable assignment?
  if (preg_match('/^\s*([a-z]\w*)\s*=\s*(.+)$/', $expr, $matches)) {
    if (in_array($matches[1], $this->vb)) { // make sure we're not assigning to a constant
      return $this->trigger("cannot assign to constant '$matches[1]'");
    }
    if (($tmp = $this->pfx($this->nfx($matches[2]))) === false) {
      return false; // get the result and make sure it's good
    }
    $this->v[$matches[1]] = $tmp; // if so, stick it in the variable array
    return $this->v[$matches[1]]; // and return the resulting value
    //===============
    // is it a function assignment?
  }
  elseif (preg_match('/^\s*([a-z]\w*)\s*\(\s*([a-z]\w*(?:\s*,\s*[a-z]\w*)*)\s*\)\s*=\s*(.+)$/', $expr, $matches)) {
    $fnn = $matches[1]; // get the function name
    if (in_array($matches[1], $this->fb)) { // make sure it isn't built in
      return $this->trigger("cannot redefine built-in function '$matches[1]()'");
    }
    $args = explode(",", preg_replace("/\s+/", "", $matches[2])); // get the arguments
    if (($stack = $this->nfx($matches[3])) === false) {
      return false; // see if it can be converted to postfix
    }
    for ($i = 0; $i < count($stack); $i++) { // freeze the state of the non-argument variables
      $token = $stack[$i];
      if (preg_match('/^[a-z]\w*$/', $token) and !in_array($token, $args)) {
        if (array_key_exists($token, $this->v)) {
          $stack[$i] = $this->v[$token];
        }
        else {
          return $this->trigger("undefined variable '$token' in function definition");
        }
      }
    }
    $this->f[$fnn] = array('args' => $args, 'func' => $stack);
    return true;
    //===============
  }
  else {
    return $this->pfx($this->nfx($expr)); // straight up evaluation, woo
  }
}