<?php

$primes 
= array ( 
  
2,    3,    5,    7,    11,   13,   17,   19,   23,   29,   31,   37,   41,   43,   47,   53,   59,   61,   67,   71,
  
73,   79,   83,   89,   97,   101,  103,  107,  109,  113,  127,  131,  137,  139,  149,  151,  157,  163,  167,  173,
  
179,  181,  191,  193,  197,  199,  211,  223,  227,  229,  233,  239,  241,  251,  257,  263,  269,  271,  277,  281,
  
283,  293,  307,  311,  313,  317,  331,  337,  347,  349,  353,  359,  367,  373,  379,  383,  389,  397,  401,  409,
  
419,  421,  431,  433,  439,  443,  449,  457,  461,  463,  467,  479,  487,  491,  499,  503,  509,  521,  523,  541,
  
547,  557,  563,  569,  571,  577,  587,  593,  599,  601,  607,  613,  617,  619,  631,  641,  643,  647,  653,  659,
  
661,  673,  677,  683,  691,  701,  709,  719,  727,  733,  739,  743,  751,  757,  761,  769,  773,  787,  797,  809,
  
811,  821,  823,  827,  829,  839,  853,  857,  859,  863,  877,  881,  883,  887,  907,  911,  919,  929,  937,  941,
  
947,  953,  967,  971,  977,  983,  991,  997,  100910131019102110311033103910491051106110631069,
  
10871091109310971103110911171123112911511153116311711181118711931201121312171223,
  
12291231123712491259127712791283128912911297130113031307131913211327136113671373,
  
13811399140914231427142914331439144714511453145914711481148314871489149314991511,
  
15231531154315491553155915671571157915831597160116071609161316191621162716371657,
  
16631667166916931697169917091721172317331741174717531759177717831787178918011811,
  
18231831184718611867187118731877187918891901190719131931193319491951197319791987,
  
19931997199920032011201720272029203920532063206920812083208720892099211121132129,
  
21312137214121432153216121792203220722132221223722392243225122672269227322812287,
  
22932297230923112333233923412347235123572371237723812383238923932399241124172423,
  
24372441244724592467247324772503252125312539254325492551255725792591259326092617,
  
26212633264726572659266326712677268326872689269326992707271127132719272927312741,
  
27492753276727772789279127972801280328192833283728432851285728612879288728972903,
  
29092917292729392953295729632969297129993001301130193023303730413049306130673079,
  
30833089310931193121313731633167316931813187319132033209321732213229325132533257,
  
32593271329933013307331333193323332933313343334733593361337133733389339134073413,
  
34333449345734613463346734693491349935113517352735293533353935413547355735593571,
  
35813583359336073613361736233631363736433659367136733677369136973701370937193727,
  
37333739376137673769377937933797380338213823383338473851385338633877388138893907,
  
39113917391939233929393139433947396739894001400340074013401940214027404940514057,
  
40734079409140934099411141274129413341394153415741594177420142114217421942294231,
  
42414243425342594261427142734283428942974327433743394349435743634373439143974409,
  
44214423444144474451445744634481448344934507451345174519452345474549456145674583,
  
45914597460346214637463946434649465146574663467346794691470347214723472947334751,
  
47594783478747894793479948014813481748314861487148774889490349094919493149334937,
  
49434951495749674969497349874993499950035009501150215023503950515059507750815087,
  
50995101510751135119514751535167517151795189519752095227523152335237526152735279,
  
52815297530353095323533353475351538153875393539954075413541754195431543754415443,
  
54495471547754795483550155035507551955215527553155575563556955735581559156235639,
  
56415647565156535657565956695683568956935701571157175737574157435749577957835791,
  
58015807581358215827583958435849585158575861586758695879588158975903592359275939,
  
59535981598760076011602960376043604760536067607360796089609161016113612161316133,
  
61436151616361736197619962036211621762216229624762576263626962716277628762996301,
  
63116317632363296337634363536359636163676373637963896397642164276449645164696473,
  
64816491652165296547655165536563656965716577658165996607661966376653665966616673,
  
66796689669167016703670967196733673767616763677967816791679368036823682768296833,
  
68416857686368696871688368996907691169176947694969596961696769716977698369916997,
  
70017013701970277039704370577069707971037109712171277129715171597177718771937207,
  
72117213721972297237724372477253728372977307730973217331733373497351736973937411,
  
74177433745174577459747774817487748974997507751775237529753775417547754975597561,
  
75737577758375897591760376077621763976437649766976737681768776917699770377177723,
  
77277741775377577759778977937817782378297841785378677873787778797883790179077919,
  
79197927793379377949795179637993800980118017803980538059806980818087808980938101,
  
81118117812381478161816781718179819182098219822182318233823782438263826982738287,
  
82918293829783118317832983538363836983778387838984198423842984318443844784618467,
  
85018513852185278537853985438563857385818597859986098623862786298641864786638669,
  
86778681868986938699870787138719873187378741874787538761877987838803880788198821,
  
88318837883988498861886388678887889389238929893389418951896389698971899990019007,
  
90119013902990419043904990599067909191039109912791339137915191579161917391819187,
  
91999203920992219227923992419257927792819283929393119319932393379341934393499371,
  
93779391939794039413941994219431943394379439946194639467947394799491949795119521,
  
95339539954795519587960196139619962396299631964396499661967796799689969797199721,
  
97339739974397499767976997819787979198039811981798299833983998519857985998719883,
  
9887990199079923992999319941994999679973 );

function 
gamma $z ) {
  if ( (int)
$z == $z && $z )
    return 
NAN;
  
$p = array (
    
0.99999999999980993,  676.5203681218851    , -1259.1392167224028,
    
771.32342877765313 , -176.61502916214059   ,  12.507343278686905,
   -
0.13857109526572012,  9.9843695780195716e-6,  1.5056327351493116e-7
    
);
  if ( 
$z 0.5 )
    return 
M_PI / ( sin M_PI $z ) * gamma $z ) );
  --
$z;
  
$x $p[0];
  for ( 
$i 1$i 9; ++$i )
    
$x += $p[$i] / ( $z $i );
  
$t $z 7.5;
  return 
sqrt M_PI ) * pow $t$z 0.5 ) * exp ( -$t ) * $x;
  }

function 
erf $x ) {
  if ( 
$x == )
    return 
0;
  
$t / ( abs $x ) / );
  
$t $t exp ( -$x $x
                 
1.26551223
                 
1.00002368 $t
                 
0.37409196 $t $t
                 
0.09678418 $t $t $t
                 
0.18628806 $t $t $t $t
                 
0.27886807 $t $t $t $t $t
                 
1.13520398 $t $t $t $t $t $t
                 
1.48851587 $t $t $t $t $t $t $t
                 
0.82215223 $t $t $t $t $t $t $t $t
                 
0.17087277 $t $t $t $t $t $t $t $t $t );
  if ( 
$x >= )
    return 
$t;
  return 
$t 1;
  }

function 
lcm $a$b ) {
  
$i 1;
  
$l min intval ($a), intval($b) );
  
$m max intval ($a), intval($b) );
  while ( 
$i $l $m != ) ++$i;
  return 
$l $i;
  }

function 
gcd $a$b ) {
  
$m max abs $a ), abs $b ) );
  
$d $m;
  for ( ; 
$d 1; --$d ) {
    if ( 
round $a ) % $d == && round $b ) % $d == )
      break;
    }
  return 
$d;
  }

function 
ncr $n$k ) {
  
$j $res 1;
  if ( 
$k || $k $n )
    return 
0;
  if ( ( 
$n $k ) < $k )
    
$k $n $k;
  while ( 
$j <= $k ) {
    
$res *= $n--;
    
$res /= $j++;
    }
  return 
$res;
  }

/* old version, pending removal; fails for 10186049
function isPrime ( $i ) {
  global $primes;
  if ( $i < 2 || ( !( $i & 1 ) && $i != 2 ) )
    return false;
  if ( $i < 10000 )
    return in_array ( $i, $primes );
  if ( $i < 100000000 ) {
    for ( $o = 0; $o < count ( $primes) && $primes[$o] <= floor ( sqrt ( $i ) ); ++$o ) {
      if ( $i % $primes[$o] == 0 )
        return false;
      }
    }
  for ( $t = 0; $t / 6 - 1 <= intval ( sqrt ( $i ) ); ++$t )
    if ( $i % ( 6 * $t - 1 ) == 0 || $i % ( 6 * $t + 1 ) == 0 )
      return false;
  return true;
  } //*/

function isPrime $i ) {
  global 
$primes;
  if ( 
$i == )
    return 
true;
  if ( 
$i || !( $i ) )
    return 
false;
  if ( 
$i 10000 )
    return 
in_array $i$primes );
  
$s floor sqrt $i ) );
  for ( 
$d 0$d $s && $d count $primes ); ++$d )
    if ( 
$i $primes[$d] == )
      return 
false;
  for ( 
$t 1667$t <= $s; ++$t )
    if ( 
$i % ( $t ) == 0
      
|| $i % ( $t ) == )
      return 
false;
  return 
true;
  }

function 
isCoprime $a$b ) {
  if ( 
$a && $b )
    return 
false;
  if ( 
$a && $b )
    return 
isCoprime ( -$a$b );
  if ( 
$a && $b )
    return 
isCoprime $a, -$b );
  if ( 
$a === && $b === )
    return 
false;
  if ( 
$a === && $b === )
    return 
false;
  
$l $a $b ? ( sqrt $b ) - ) / : ( sqrt $a ) - ) / 6;
  for ( 
$k 1$k $l; ++$k ) {
    
$t1 $a % ( $k );
    
$t2 $b % ( $k );
    if ( 
$t1 === && $t2 === 0)
      return 
false;
    
$t1 $a % ( $k );
    
$t2 $b % ( $k );
    if ( 
$t1 === && $t2 === 0)
      return 
false;
    }
  return 
true;
  }

function 
factor $i ) {
  global 
$primes;
  if ( 
$i === )
    return array();
  
$factors = array ();
  if ( 
$i ) {
    
$factors[] = -1;
    
$i *= -1;
    }
  if ( 
in_array $i$primes ) ) {
    
$factors[] = $i;
    return 
$factors;
    }
  for ( 
$t 0$t count $primes ) && $i !== 1; ++$t ) {
    if ( 
$i $primes[$t] === ) {
      
$factors[] = $primes[$t];
      
$i /= $primes[$t];
      --
$t;
      continue;
      }
    }
  if ( 
$i === )
    return 
$factors;
  for ( 
$t 1668$i !== 1; ++$t ) { // it has a prime factor larger than 10000
    
$td 0;
    if ( 
isPrime $t ) ) { // Here's a prime; test it
      
if ( $i % ( $t ) === ) {
        
$factors[] = $t 1;
        
$i /= $t 1;
        ++
$td;
        }
      }
    if ( 
isPrime $t ) ) { // Here's a prime; test it
      
if ( $i & ( $t ) === ) {
        
$factor[] = $t 1;
        
$i /= $t 1;
        ++
$td;
        }
      }
    
$t -= $td;
    }
  return 
$factors;
  }

function 
ellipse_circ_r1 $a$b ) {
  return 
M_PI * ( * ( $a $b ) - sqrt ( ( $a $b ) * ( $a $b ) ) );
  }

function 
ellipse_circ_r2 $a$b ) {
  
$h = ( $a $b ) / ( $a $b );
  
$h *= $h;
  return 
M_PI * ( $a $b ) * ( $h / ( 10 sqrt $h ) ) );
  }

function 
ellipse_circ_sum $a$b ) {
  
$df = function ( $n ) { // double factorial
    
$a 1;
    for ( 
$i $n$i 0$i -= )
      
$a *= $i;
    return 
$a;
    };
  
$fact = function ( $n ) {
    
$o 1;
    for ( 
$i 2$i <= $n; ++$i )
      
$o *= $i;
    return 
$o;
    };
  
$h = ( $a $b ) / ( $a $b );
  
$h *= $h;
  
$o 1;
  
$hp 1;
  for ( 
$k 1$k 53; ++$k ) {
    
$hp *= $h;
    
$l = ( $k << ) - 1;
    
$l *= $l;
    
$l $hp $l;
    
$r $df ( ( $k << ) - ) / ( ( << $k ) * $fact $k ) );
    
$r *= $r;
    if ( 
is_nan ($l) || is_nan ($r) || is_infinite ($l) || is_infinite ($r) )
      break;
    
$o += $l $r;
    }
  
$o *= M_PI * ( $a $b );
  return 
$o;
  }

function 
bottom $arr$sub1 NULL$sub2 NULL ) {
  if ( !
is_array $arr ) )
    throw new 
Exception "non-array argument passed to bottom" );
  if ( empty ( 
$arr ) )
    throw new 
Exception "empty array passed to bottom" );
  if ( 
$sub1 === NULL )
    return 
$arr[count($arr)-1];
  if ( 
$sub2 === NULL )
    return 
$arr[count($arr)-1][$sub1];
  return 
$arr[count($arr)-1][$sub1][$sub2];
  }

class 
rpCalc {
  const 
VERSION_MAJOR "1",
        
VERSION_MINOR "12",
        
VERSION_SUB   "0";
  
  private 
$loops = array (),
          
$stack = array (),
          
$tokens,
          
$mode 'dec',
          
$storage,
          
$answers,
          
$key,
          
$result,
          
$state 0;
  
  public static function 
version () {
    return array ( 
rpCalc::VERSION_MAJORrpCalc::VERSION_MINORrpCalc::VERSION_SUB );
    }
  
  public function 
__construct ( &$storage$key ) {
    
$this->storage = &$storage;
    
$this->key $key;
    }
  
  private function 
proc_line_dec $instr ) {
    
$tokens = array ();
    
$tokstr "";
    
$mode 0;
    for ( 
$i 0$i strlen $instr ); ++$i ) {
      switch ( 
$instr[$i] ) {
        case 
" ":  case "\t": case "\r": case "\n":
          if ( 
$mode != ) {
            if ( 
strlen $tokstr ) != ) {
              
$tokens[] = $tokstr;
              
$tokstr "";
              }
            
$mode 0;
            }
          break;
        case 
"a": case "A": case "b": case "B": case "c": case "C": case "d": case "D":
        case 
"e": case "E": case "f": case "F": case "g": case "G": case "h": case "H":
        case 
"i": case "I": case "j": case "J": case "k": case "K": case "l": case "L":
        case 
"m": case "M": case "n": case "N": case "o": case "O": case "p": case "P":
        case 
"q": case "Q": case "r": case "R": case "s": case "S": case "t": case "T":
        case 
"u": case "U": case "v": case "V": case "w": case "W": case "x": case "X":
        case 
"y": case "Y": case "z": case "Z": case "_":
          if ( 
$mode != ) {
            
$mode 1;
            if ( 
strlen $tokstr ) != ) {
              
$tokens[] = $tokstr;
              
$tokstr "";
              }
            }
          
$tokstr .= $instr[$i];
          break;
        case 
"1": case "2": case "3": case "4": case "5": case ".":
        case 
"6": case "7": case "8": case "9": case "0":
          if ( 
$mode ) {
            
$mode 2;
            
$tokens[] = $tokstr;
            
$tokstr "";
            }
          if ( 
$mode == ) {
           
$mode 2;
            if ( 
count($tokens) > && $tokenscount($tokens)-] == '-' && $instr[$i-1] == '-' ) {
              
$tokstr '-';
              
array_pop $tokens );
              }
            }
          if ( 
$mode == || $mode == )
            
$tokstr .= $instr[$i];
          break;
        default:
          if ( 
$mode != ) {
            
$tokens[] = $tokstr;
            
$tokstr "";
            
$mode 0;
            }
          
$_ substr $instr$i);
          switch ( 
$_ ) {
            case 
"<<>":
              
$tokens[] = "<<>";
              
$_ "   ";
              
$i += 2;
              break;
            case 
"<>>":
              
$tokens[] = "<>>";
              
$_ "   ";
              
$i += 2;
              break;
            }
          
$_[2] = " ";
          switch ( 
$_ ) {
            case 
"<< ":
              
$tokens[] = "<<";
              
$_ "   ";
              
$i += 1;
              break;
            case 
">> ":
              
$tokens[] = ">>";
              
$_ "   ";
              
$i += 1;
              break;
            case 
">= ":
              
$tokens[] = ">=";
              
$_ "   ";
              
$i += 1;
              break;
            case 
"<= ":
              
$tokens[] = "<=";
              
$_ "   ";
              
$i += 1;
            break;
          }
        if ( 
$_ != "   " )
          
$tokens[] = $instr[$i];
          break;
        }
      }
    if ( 
strlen $tokstr ) != )
      
$tokens[] = $tokstr;
    
$this->tokens $tokens;
    return 
$tokens;
    }
  
  private function 
proc_line_bin $line ) {
    
$tokens = array();
    for ( 
$i 0$i strlen $line ); ++$i )
      switch ( 
$line[$i] ) {
        case 
' ': case '\t': case '\r': case '\n': break; // Skip all white space
        
case '0': case '1':
          
$tokens[] = $line[$i]; // Push all numbers to the token list
          
break;
        case 
'+': case '|':
          
$tokens[] = '|'// OR
          
break;
        case 
'*': case '&':
          
$tokens[] = '&'// AND
          
break;
        case 
'^':
          
$tokens[] = '^'// XOR
          
break;
        case 
'\'': case '!':
          
$tokens[] = '!'// NOT
          
break;
        case 
'>':
          
$tokens[] = '>'// Implies
          
break;
        case 
'=':
          
$tokens[] = '='// Biconditional (NXOR)
          
break;
        }
    
$this->tokens $tokens;
    return 
$tokens;
    }

  private function 
eval_tokens_dec $tokens NULL$defs = array (), $nestlevel ) {
    if ( !
is_array $tokens ) )
      
$tokens $this->tokens;
    for ( 
$i 0$i count $tokens ); ++$i ) {
      if ( 
is_numeric $tokens[$i] ) ) {
        
array_push $this->stack$tokens[$i] );
        continue;
        }
      switch ( 
$tokens[$i] ) {
        
// Meta
        
case "@":
          
$this->state += 2;
          break;
        
        
// NaN
        
case "NaN":
        case 
"NAN":
          
array_push $this->stackNAN );
          break;
        
        
// Stack manipulation
        
case "x":
          
$temp = array ( array_pop $this->stack ), array_pop $this->stack ) );
          
array_push $this->stack$temp[0] );
          
array_push $this->stack$temp[1] );
          break;
        case 
"r":
          
array_pop $this->stack );
          break;
        case 
"v":
          
$temp = array ( array_pop $this->stack ), array_pop $this->stack ), array_pop $this->stack ) );
          
array_push $this->stack$temp[1] );
          
array_push $this->stack$temp[0] );
          
array_push $this->stack$temp[2] );
          break;
        case 
"d":
          
array_push $this->stack$this->stack[count($this->stack)-1] );
          break;
        case 
"rr":
          
array_push $this->stackarray_shift $this->stack ) );
          break;
        case 
"rl":
          
array_unshift $this->stackarray_pop $this->stack ) );
          break;
        case 
"count":
          
array_push $this->stackcount $this->stack ) );
          break;
        case 
"flip":
          
$this->stack array_reverse $this->stack );
          break;
        case 
"stack_copy":
          
$this->stack array_merge $this->stack$this->stack );
          break;
        case 
"stack_mirror":
          
$this->stack array_merge $this->stackarray_reverse $this->stack ) );
          break;
        
        
// Control functions
        
case "terminate":
          return;
        case 
"yield":
          
//yield;
          
break;
          
        
        
// Constants
        
case "pi":
          
array_push $this->stackM_PI );
          break;
        case 
"e":
          
array_push $this->stackM_E );
          break;
        
        
// Arithmatic
        
case "+":
          
array_push $this->stackarray_pop $this->stack ) + array_pop $this->stack ) );
          break;
        case 
"-":
          
$a array_pop $this->stack );
            
$b array_pop $this->stack );
          if ( 
is_infinite $a ) && is_infinite $b ) )
            
array_push $this->stackNAN );
          else
            
array_push $this->stack$b $a );
          break;
        case 
"*":
          
$a array_pop $this->stack );
          
$b array_pop $this->stack );
          if ( 
is_infinite $a ) && $b == || $a == && is_infinite $b ) )
            
array_push $this->stackNAN );
          else
            
array_push $this->stack$a $b );
          break;
        case 
"/":
          
$b array_pop $this->stack );
          
$a array_pop $this->stack );
          if ( 
$b == )
            
array_push $this->stackNAN );
          else
            
array_push $this->stack$a $b );
          break;
        case 
"%":
        
$temp array_pop $this->stack );
          
array_push $this->stackfmod array_pop $this->stack ), $temp ) );
          break;
        case 
"^":
          
$a array_pop $this->stack );
          
$b array_pop $this->stack );
          if ( 
is_infinite $a ) && $b == || $a == && is_infinite $b ) )
            
array_push $this->stackNAN );
          else
            
array_push $this->stackpow $b$a ) );
          break;
        case 
"\\":
          
$tmp array_pop $this->stack );
          if ( 
$tmp == )
            
array_push $this->stackNAN );
          else
            
array_push $this->stack$tmp );
          break;
        
        
// Power functions
        
case "abs":
          
array_push $this->stackabs array_pop $this->stack ) ) );
          break;
        case 
"sqrt":
          
array_push $this->stacksqrt array_pop $this->stack ) ) );
          break;
        case 
"crt":
          
array_push $this->stackpow array_pop $this->stack ), ) );
          break;
        case 
"root":
          
$temp array_pop $this->stack );
          
array_push $this->stackpow array_pop $this->stack ), $temp ) );
          break;
        
        
// Logarithms
        
case "ln":
          
array_push $this->stacklog array_pop $this->stack ) ) );
          break;
        case 
"lc":
          
array_push $this->stacklog array_pop $this->stack ), 10 ) );
          break;
        case 
"lb":
          
array_push $this->stacklog array_pop $this->stack ), ) );
          break;
        case 
"log":
          
$temp array_pop $this->stack );
          
array_push $this->stacklog array_pop $this->stack ), $temp ) );
          break;
        
        
// Trig
        
case "sin":
          
array_push $this->stacksin array_pop $this->stack ) ) );
          break;
        case 
"cos":
          
array_push $this->stackcos array_pop $this->stack ) ) );
          break;
        case 
"tan":
          
array_push $this->stacktan array_pop $this->stack ) ) );
          break;
        case 
"sec":
          
$tmp array_pop $this->stack );
          if ( 
$tmp != )
            
array_push $this->stacksin $tmp ) );
          else
            
array_push $this->stackINF );
          break;
        case 
"csc":
          
array_push $this->stackcos array_pop $this->stack ) ) );
          break;
        case 
"cot":
          
array_push $this->stacktan array_pop $this->stack ) ) );
          break;
        case 
"sinh":
          
array_push $this->stacksinh array_pop $this->stack ) ) );
          break;
        case 
"cosh":
          
array_push $this->stackcosh array_pop $this->stack ) ) );
          break;
        case 
"tanh":
          
array_push $this->stacktanh array_pop $this->stack ) ) );
          break;
        case 
"sech":
          
array_push $this->stacksinh array_pop $this->stack ) ) );
          break;
        case 
"csch":
          
array_push $this->stacksinh array_pop $this->stack ) ) );
          break;
        case 
"coth":
          
array_push $this->stacktanh array_pop $this->stack ) ) );
          break;
        case 
"asin":
          
array_push $this->stackasin array_pop $this->stack ) ) );
          break;
        case 
"acos":
          
array_push $this->stackacos array_pop $this->stack ) ) );
          break;
        case 
"atan":
          
array_push $this->stackatan array_pop $this->stack ) ) );
          break;
        case 
"atan2":
          
$temp array_pop $this->stack );
          
array_push $this->stackatan2 array_pop $this->stack ), $temp ) );
          break;
        case 
"asec":
          
array_push $this->stackacos array_pop $this->stack ) ) );
          break;
        case 
"acsc":
          
array_push $this->stackasin array_pop $this->stack ) ) );
          break;
        case 
"acot":
          
array_push $this->stackatan array_pop $this->stack ) ) );
          break;
        case 
"asinh":
          
array_push $this->stackasinh array_pop $this->stack ) ) );
          break;
        case 
"acosh":
          
array_push $this->stackacosh array_pop $this->stack ) ) );
          break;
        case 
"atanh":
          
array_push $this->stackatanh array_pop $this->stack ) ) );
          break;
        case 
"asech":
          
array_push $this->stackacosh array_pop $this->stack ) ) );
          break;
        case 
"acsch":
          
array_push $this->stackasinh array_pop $this->stack ) ) );
          break;
        case 
"acoth":
          
array_push $this->stackatanh array_pop $this->stack ) ) );
          break;
        
        
// Random numbers
        
case "rand_max":
          
array_push $this->stackmt_getrandmax () );
          break;
        case 
"rand":
          
array_push $this->stackmt_rand () );
          break;
        case 
"randf":
          
array_push $this->stackmt_rand () / mt_getrandmax () );
          break;
        case 
"randl":
          
array_push $this->stackmt_rand round array_pop $this->stack ) ), mt_getrandmax() ) );
          break;
        case 
"randu":
          
array_push $this->stackmt_rand 0round array_pop  $this->stack ) ) ) );
          break;
        case 
"randb":
          
$temp round array_pop $this->stack ) );
          
array_push $this->stackmt_rand round array_pop $this->stack ) ), $temp ) );
          break;
        
        
// Rounding
        
case "round":
          
array_push $this->stackround array_pop $this->stack ) ) );
          break;
        case 
"roundn":
          
$temp array_pop $this->stack );
          
array_push $this->stackround array_pop $this->stack ), round $temp ) ) );
          break;
        case 
"floor":
          
array_push $this->stackfloor array_pop $this->stack ) ) );
          break;
        case 
"ceil":
          
array_push $this->stackceil array_pop $this->stack ) ) );
          break;
        
        
// Manipulating collections of data
        
case "sort":
          
sort $this->stack );
          break;
        case 
"sortn":
          
$n array_pop $this->stack );
          
$tmp array_slice $this->stack, -$n );
          
sort $tmp );
          
$this->stack array_merge array_slice $this->stack0, -$n ), $tmp );
          break;
        case 
"rsort":
          
rsort $this->stack );
          break;
        case 
"rsortn":
          
$n array_pop $this->stack );
          
$tmp array_slice $this->stack, -$n );
          
rsort $tmp );
          
$this->stack array_merge array_slice $this->stack0, -$n ), $tmp );
          break;
        case 
"shuffle":
          
shuffle $this->stack );
          break;
        case 
"shufflen":
          
$n array_pop $this->stack );
          
$tmp array_slice $this->stack, -$n );
          
shuffle $tmp );
          
$this->stack array_merge array_slice $this->stack0, -$n ), $tmp );
          break;
        case 
"setequal":
          
$n array_pop $this->stack );
          if ( 
array_slice $this->stack, -$n) == array_slice $this->stack, -$n$n ) )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
"setnequal":
          
$n array_pop $this->stack );
          if ( 
array_slice $this->stack, -$n) == array_slice $this->stack, -$n$n ) )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
"runcount":
          
$n array_pop $this->stack );
          
$c 1;
          for ( ; 
bottom $this->stack ) == $n; ++$c )
            
array_pop $this->stack );
          
array_push $this->stack$n );
          
array_push $this->stack$c );
          break;
        
        
// min/max
        
case "min":
          
array_push $this->stackmin $this->stack ) );
          break;
        case 
"pmin":
          
array_push $this->stackmin array_slice $this->stack, -array_pop $this->stack ) ) ) );
          break;
        case 
"max":
          
array_push $this->stackmax $this->stack ) );
          break;
        case 
"pmax":
          
array_push $this->stackmax array_slice $this->stack, -array_pop $this->stack ) ) ) );
          break;
        
        
// Loops
        //
        // $this->loops => array ( array (
        //   [0] => return index,
        //   [1] => iteration/success total,
        //   [2] => iteration/succuss current,
        //   [3] => state, 0=iteration, 1=success
        //   ), ... )
        
case "[":
          if ( 
count $this->stack ) == )
            throw new 
Exception "Loop failed (empty stack)" );
          if ( 
is_nan bottom $this->stack ) ) )
            throw new 
Exception "Loop failed: non numeric iteration count" );
          if ( isset ( 
$tokens[$i+1] ) && $tokens[$i+1] == ']' ) { // empty loop optimization
            
array_pop $this->stack );
            
$i++;
            continue 
2;
            }
          
array_push $this->loops, array ( $iround array_pop $this->stack ) ), 0$this->state ) );
          break;
        case 
"]":
          if ( 
count $this->loops ) == )
            throw new 
Exception "Loop failed (nothing to return to)" );
          if ( 
bottom $this->loops) > bottom $this->loops) - ) {
            
array_pop $this->loops );
            continue 
2;
            }
          
$i bottom $this->loops);
          if ( 
bottom $this->loops) == ) {
            
$this->loops[count($this->loops)-1][2] += 1;
            }
          else
            throw new 
Exception "Error: reached end of finite-success loops without encountering either pass or fail statement" );
          break;
        case 
"pass":
          if ( 
count $this->loops ) == )
            throw new 
Exception "Loop failed (nothing to return to)" );
          if ( 
bottom $this->loops) != )
            throw new 
Exception "pass can only be used inside a finite-success loop" );
          
$this->loops[count($this->loops)-1][2] += 1;
          if ( 
bottom $this->loops) < bottom $this->loops) )
            
$i bottom $this->loops);
          else {
            while ( 
$this->tokens[$i++] != "]" );
            
array_pop $this->loops );
            }
          break;
        case 
"fail":
          if ( 
count $this->loops ) == )
            throw new 
Exception "Loop failed (nothing to return to)" );
          if ( 
bottom $this->loops) != )
            throw new 
Exception "fail can only be used inside a finite-success loop" );
          
$i bottom $this->loops);
          break;
        case 
"l":
          switch ( 
$this->state ) {
            case 
0:
              
array_push $this->stackbottom $this->loops) );
              break;
            case 
1:
              
array_push $this->stackbottom $this->loops) - bottom $this->loops) );
              break;
            }
          break;
        case 
"break":
          if ( !
count $this->loops ) )
            throw new 
Exception "break can only be used inside loops" );
          
$j bottom $this->loops);
          
array_pop $this->loops );
          for ( 
$tmp 0$tokens[$j] != ']' || $tmp != 0; ++$j ) {
            if ( 
$tokens[$j] == '[' )
              ++
$tmp;
            elseif ( 
$tokens[$j] == ']' )
              --
$tmp;
            }
          
$i $j;
          break;
        case 
"continue":
          if ( !
count $this->loops ) )
            throw new 
Exception "continue can only be used inside loops" );
          if ( 
bottom $this->loops) == )
            throw new 
Exception "continue cannot be used inside finite-success loops" );
          
$this->loops[count($this->loops)-1][2] += 1;
          
$i bottom $this->loops);
          break;
        
        
// Accept, but ignore
        
case "{":
        case 
"}":
          break;
        
        
// Custom functions
        
case "(":
          
$tmp array_slice $tokens$i );
          for ( 
$j count $tmp ) - 1$j >= 0; --$j ) {
            if ( 
$tmp[$j] == ')' )
              break;
            if ( 
$j == )
              throw new 
Exception "Error: incomplete function definition" );
            }
          ++
$i;
          
$name $tokens[$i++];
          if ( !
preg_match "/[a-zA-Z_][a-zA-Z0-9_]*/"$name ) )
            throw new 
Exception "Invalid name for function: \"$name\"" );
          if ( 
$tokens[$i++] != ":" )
            throw new 
Exception "Malformed function definition for \"$name\"" );
          
$a1 $a2 = array ();
          while ( 
$tokens[$i] != ")" && $tokens[$i] != ":" )
            
$a1[] = $tokens[$i++];
          if ( 
$tokens[$i] == ":" ) {
            ++
$i;
            while ( 
$tokens[$i] != ")" )
              
$a2[] = $tokens[$i++];
            }
          if ( empty ( 
$a2 ) )
            
$this->storage["func"][$this->key][$name] = array ( $a1, array () );
          else
            
$this->storage["func"][$this->key][$name] = array ( $a2$a1 );
          break;
        case 
")":
          throw new 
Exception "Error: unexpected ')'" );
          break;
        case 
"ret":
          if ( 
$nestlevel === )
            throw new 
Exception "Not in function from which to return" );
          return;
        
        
// Comparison
        
case "=":
          
$b array_pop $this->stack );
          
$a array_pop $this->stack );
          if ( 
$this->state != ) {
            
array_push $this->stack$a );
            
array_push $this->stack$b );
            }
          if ( 
$a == $b )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
"<":
          
$b array_pop $this->stack );
          
$a array_pop $this->stack );
          if ( 
$this->state != ) {
            
array_push $this->stack$a );
            
array_push $this->stack$b );
            }
          if ( 
$a $b )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
">":
          
$b array_pop $this->stack );
          
$a array_pop $this->stack );
          if ( 
$this->state != ) {
            
array_push $this->stack$a );
            
array_push $this->stack$b );
            }
          if ( 
$a $b )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
"<=":
          
$b array_pop $this->stack );
          
$a array_pop $this->stack );
          if ( 
$this->state != ) {
            
array_push $this->stack$a );
            
array_push $this->stack$b );
            }
          if ( 
$a <= $b )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
">=":
          
$b array_pop $this->stack );
          
$a array_pop $this->stack );
          if ( 
$this->state != ) {
            
array_push $this->stack$a );
            
array_push $this->stack$b );
            }
          if ( 
$a >= $b )
            
array_push $this->stack);
          else
            
array_push $this->stack);
          break;
        case 
"!":
          
$a array_pop $this->stack );
          if ( 
$this->state != )
            
array_push $this->stack$a );
          if ( 
$a !== 0)
            
array_push $this->stack0);
          else
            
array_push $this->stack);
          break;
        case 
"isInf":
          
$a array_pop $this->stack );
          if ( 
$this->state != )
            
array_push $this->stack$a );
          
array_push $this->stackis_infinite $a ) );
          break;
        case 
"isNaN":
          
$a array_pop $this->stack );
          if ( 
$this->state != )
            
array_push $this->stack$a );
          
array_push $this->stackis_nan $a ) );
          break;
        
        
// Bitwise
        
case "and":
        case 
"&":
          
array_push $this->stackround array_pop $this->stack ) ) & round array_pop $this->stack ) ) );
          break;
        case 
"or":
        case 
"|":
          
array_push $this->stackround array_pop $this->stack ) ) | round array_pop $this->stack ) ) );
          break;
        case 
"xor":
          
array_push $this->stackround array_pop $this->stack ) ) ^ round array_pop $this->stack ) ) );
          break;
        case 
"nand":
          
array_push $this->stack, ~( round array_pop $this->stack ) ) & round array_pop $this->stack ) ) ) );
          break;
        case 
"nor":
          
array_push $this->stack, ~( round array_pop $this->stack ) ) | round array_pop $this->stack ) ) ) );
          break;
        case 
"equiv":
        case 
"nxor":
          
array_push $this->stack, ~( round array_pop $this->stack ) ) ^ round array_pop $this->stack ) ) ) );
          break;
        case 
"imply":
          
$temp round array_pop $this->stack ) );
          
array_push $this->stack, ~( round array_pop $this->stack ) ) & ~$temp ) );
          break;
        case 
"not":
        case 
"~":
          
array_push $this->stack, ~round array_pop $this->stack ) ) );
          break;
        case 
"<<":
          
$temp array_pop $this->stack );
          
array_push $this->stackround array_pop $this->stack ) ) << $temp );
          break;
        case 
">>":
          
$temp array_pop $this->stack );
          
array_push $this->stackround array_pop $this->stack ) ) >> $temp );
          break;
        case 
"brl":
        case 
"<<>":
          
$tmp = array ( array_pop $this->stack ), str_pad decbin array_pop $this->stack ) ), strlen decbin ( -) ), '0'STR_PAD_LEFT ) );
          
array_push $this->stackbindec substr $tmp[1], $tmp[0] ) . substr $tmp[1], 0$tmp[0] ) ) );
          break;
        case 
"brr":
        case 
"<>>":
          
$tmp = array ( array_pop $this->stack ), str_pad decbin array_pop $this->stack ) ), strlen decbin ( -) ), '0'STR_PAD_LEFT ) );
          
array_push $this->stackbindec substr $tmp[1], -$tmp[0] ) . substr $tmp[1], 0, -$tmp[0] ) ) );
          break;
        
        
// Storage
        
case "store":
          
$temp array_pop $this->stack );
          
$this->storage['data'][$_REQUEST['key']][$temp] = array_pop $this->stack );
          break;
        case 
"get":
          
$temp array_pop $this->stack );
          if ( !isset ( 
$this->storage['data'][$_REQUEST['key']][$temp] ) )
            throw new 
Exception "No data in slot $temp);
          
array_push $this->stack$this->storage['data'][$_REQUEST['key']][$temp] );
          break;
        case 
"erase":
          
$temp array_pop $this->stack );
          if ( isset ( 
$this->storage['data'][$_REQUEST['key']][$temp] ) )
            unset ( 
$this->storage['data'][$_REQUEST['key']][$temp] );
          else
            throw new 
Exception "Nothing in slot $temp to erase" );
          break;
        
        
// Stacks
        
case "spush":
          
$tmp array_pop $this->stack );
          
$this->storage['stats'][$_REQUEST['key']][$tmp][] = array_pop($this->stack);
          break;
        case 
"spop":
          
array_push $this->stackarray_pop $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"serase":
          unset ( 
$this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] );
          break;
        case 
"sdump":
          
$this->result implode " "$this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] );
          return;
        case 
"scount":
          
array_push $this->stackcount $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
          
        
        
// Special functions
        
case "fib":
          
$n array_pop $this->stack );
          
array_push $this->stack, ( pow sqrt ), $n ) - pow sqrt ), $n ) ) / ( ( << $n ) * sqrt ) ) );
          break;
        case 
"gamma":
          
array_push $this->stackgamma array_pop $this->stack ) ) );
          break;
        case 
"lng":
          
array_push $this->stacklog gamma array_pop $this->stack ) ) ) );
          break;
        case 
"erf":
          
array_push $this->stackerf array_pop $this->stack ) ) );
          break;
        case 
"erfc":
          
array_push $this->stackerf array_pop $this->stack ) ) );
          break;
        
        
// Stats functions
        
case "aad":
          
array_push $this->stackaad $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"mean":
          
array_push $this->stackmean $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"median":
          
array_push $this->stackmedian $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"stdDev":
          
array_push $this->stackstdDev $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"skew":
          
array_push $this->stackskew $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"kurt":
          
array_push $this->stackkurt $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"popStdDev":
          
array_push $this->stackpopStdDev $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"popSkew":
          
array_push $this->stackpopSkew $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"popKurt":
          
array_push $this->stackpopKurt $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)] ) );
          break;
        case 
"moment":
          
$m array_pop $this->stack );
          
array_push $this->stackmoment $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)], $m ) );
          break;
        case 
"popMoment":
          
$m array_pop $this->stack );
          
array_push $this->stackpopMoment $this->storage['stats'][$_REQUEST['key']][array_pop($this->stack)], $m ) );
          break;
        
        
// Probability functions
        
case "ncr":
          
$temp = array ( array_pop $this->stack ), array_pop $this->stack ) );
          
array_push $this->stackncr $temp[1], $temp[0] ) );
          break;
        
        
// Integer functions /*/
        
case "lcm":
          
array_push $this->stacklcm array_pop $this->stack ), array_pop $this->stack ) ) );
          break;
        case 
"gcd":
          
array_push $this->stackgcd array_pop $this->stack ), array_pop $this->stack ) ) );
          break;
        
        
// Prime Number Functions
        
case "isPrime":
          
array_push $this->stackisPrime array_pop $this->stack ) ) ? );
          break;
        case 
"isCoprime":
          
array_push $this->stackisCoprime array_pop $this->stack ), array_pop $this->stack ) ) ? );
          break;
        case 
"factor":
          
$tmp factor array_pop $this->stack ) );
          foreach ( 
$tmp as $t )
            
array_push $this->stack$t );
          
array_push $this->stackcount $tmp ) );
          break;
        
        
// Ellipse circumference
        
case "ecircr1":
          
array_push $this->stackellipse_circ_r1 array_pop $this->stack ), array_pop $this->stack ) ) );
          break;
        case 
"ecircr2":
          
array_push $this->stackellipse_circ_r2 array_pop $this->stack ), array_pop $this->stack ) ) );
          break;
        case 
"ecirc":
          
array_push $this->stackellipse_circ_sum array_pop $this->stack ), array_pop $this->stack ) ) );
          break;
        
        
// Misc
        
case 'version':
          
array_push $this->stackrpCalc::VERSION_MAJOR );
          
array_push $this->stackrpCalc::VERSION_MINOR );
          
array_push $this->stackrpCalc::VERSION_SUB );
          break;
        case 
"?":
          if ( !
array_pop $this->stack ) ) {
            ++
$i;
            if ( 
$tokens[$i] == '{' )
              while ( 
$tokens[$i] != '}' && $i count $tokens ) )
                ++
$i;
            }
          break;
        case 
"ans":
          if ( !isset ( 
$this->storage["ans"][$this->key] ) )
            throw new 
Exception "Answer not available" );
          else
            
array_push $this->stack$this->storage["ans"][$this->key] );
          break;
        case 
"expr_tok_dump":
          
$this->stack $tokens;
          return;
          
        default:
          if ( isset ( 
$this->storage["func"][$this->key][$tokens[$i]] ) ) {
            
$defs_send = array ();
            
$names array_reverse $this->storage["func"][$this->key][$tokens[$i]][1] );
            foreach ( 
$names as $name )
              
$defs_send[$name] = array_pop $this->stack );
            
$this->eval_tokens_dec $this->storage["func"][$this->key][$tokens[$i]][0], $defs_send$nestlevel );
            }
          elseif ( isset ( 
$defs[$tokens[$i]] ) )
            
array_push $this->stack$defs[$tokens[$i]] );
          else
            throw new 
Exception "unrecognised token \"" $tokens[$i] . "\"" . ( strlen $tokens[$i] ) == ? ( " (" ord $tokens[$i] ) . ")" ) : ""  ) ); //*/
        
}
      if ( 
$this->state != )
        --
$this->state;
      }
    
$this->answers[] = count($this->stack)==NAN $this->stack[count($this->stack)-1];
    
$this->result $this->answers[count($this->answers)-1];
    }
  
  private function 
eval_tokens_bin $tokens NULL ) {
    if ( !
is_array $tokens ) )
      
$tokens $this->tokens;
    
var_dump $tokens ); throw new Exception ();
    for ( 
$i 0$i count $tokens ); ++$i ) {
      switch ( 
$tokens[$i] ) {
        case 
'0': case '1':
          
array_push $this->stack$tokens[$i] );
          break;
        case 
'|':
          
array_push $this->stackarray_pop $this->stack ) | array_pop $this->stack ) );
          break;
        case 
'&':
          
array_push $this->stackarray_pop $this->stack ) & array_pop $this->stack ) );
          break;
        case 
'!':
          
array_push $this->stack, !array_pop $this->stack ) );
          break;
        case 
'^':
          
array_push $this->stackarray_pop $this->stack ) ^ array_pop $this->stack ) );
          break;
        case 
'>':
          
array_push $this->stack, !array_pop $this->stack ) || array_pop $this->stack ) );
          break;
        case 
'=':
          
array_push $this->stackarray_pop $this->stack ) == array_pop $this->stack ) );
          break;
        default:
          throw new 
Exception "Unrecognised token: " $tokens[$i] );
        }
      }
    }
  
  public function 
invalidate $key ) {
    unset ( 
$this->storage['ans'][$key] );
    unset ( 
$this->storage['data'][$key] );
    return 
true;
    }
  
  public function 
push_answer $ans ) {
    
$this->answers[] = $ans;
    }
  
  public function 
get_token_count () {
    return 
count $this->tokens );
    }
  
  public function 
get_token $n ) {
    if ( 
count $this->tokens ) >= $n )
      return 
NULL;
    return 
$this->tokens[$n];
    }
  
  public function 
get_tokens () {
    return 
$this->tokens;
    }
  
  public function 
get_stack_size () {
    return 
count $this->stack );
    }
  
  public function 
get_stack_element $n ) {
    if ( 
count $this->stack ) >= $n )
      return 
NULL;
    return 
$this->stack[$n];
    }
  
  public function 
get_stack () {
    return 
$this->stack;
    }
  
  public function 
clear_stack () {
    
$this->stack = array ();
    }
  
  public function 
mode $m NULL ) {
    if ( 
$m !== NULL )
      
$this->mode $m;
    return 
$this->mode;
    }
  
  public function 
proc_line $line ) {
    if ( 
$this->mode == 'dec' ) {
      
$this->proc_line_dec $line );
      }
    elseif ( 
$this->mode == 'bin' ) {
      
$this->proc_line_bin $line );
      }
    return 
$this;
    }
  
  public function 
parse $tokens NULL$defs NULL ) {
    if ( 
$this->mode == 'dec' ) {
      
$this->eval_tokens_dec $tokens$defs );
      }
    elseif ( 
$this->mode == 'bin' ) {
      
$this->eval_tokens_bin $tokens$bin );
      }
    else die ( 
'failed to detect mode' );
    return 
$this;
    }
  
  public function 
result () {
    if ( 
count $this->stack ) == )
      return array (
        
'stack'  => array (),
        
'bottom' => NULL,
        
'count'  => 0
        
);
    return array ( 
      
'stack'  => $this->stack,
      
'bottom' => $this->stack[count($this->stack)-1],
      
'count'  => count $this->stack )
      );
    }
  }