tags:

views:

115

answers:

4

I have 3 variables like this: $first = 2; $second = 5; $operation = '*';

how can I programaticly assign the solution to this math problem to the $answer variable? I have tried eval(), but that does not work.

+4  A: 
function add($a, $b) {
    return $a + $b;
}

function multiply($a, $b) {
    return $a * $b;
}

function divide($a, $b) {
    return $a / $b;
}

$operations = array(
    '+' => 'add',
    '*' => 'multiply',
    '/' => 'divide',
);

$a = 2;
$b = 5;
$operation = '*';

echo $operations[$operation]($a, $b);
Ionuț G. Stan
I accepted richadams answer because it was simpler.
Unkwntech
That's ok. It's indeed simpler, but don't forget to filter input if you're going to eval it.
Ionuț G. Stan
All the input is coming from me it is being built randomly.
Unkwntech
+3  A: 

eval() should work perfectly fine for something like this. Remember that eval() returns NULL though, unless you tell it to return something.

<?php
$first = 3;
$second = 4;
$operation = "*";

$answer = eval('return '.$first.$operation.$second.';');

echo $answer;
?>
Rich Adams
This is perfect thanks.
Unkwntech
Remember to clean and verify the input! If any of the three variables are set by a user they can potentially be used for injection attacks!
Mats Fredriksson
All the input is coming from me it is being built randomly.
Unkwntech
A: 

It works fine for me:

var_dump(eval("return $first $operator $second;"));

But eval is evil. You should better use a function like this:

function foobar($operator)
{
    $args = func_get_args();
    array_shift($args);
    switch ($operator) {
    case "*":
        if (count($args) < 1) {
            return false;
        }
        $result = array_shift($args) * array_shift($args);
        break;
    /*
        …
    */
    }
    if (count($args)) {
        return call_user_func_array(__FUNCTION__, array_merge(array($operator, $result), $args));
    }
    return $result;
}
var_dump(foobar("*", 3, 5, 7));
Gumbo
eval is not evil if it is used correctly.
Unkwntech
+1  A: 

If you are planning on doing this calculation often, I would strongly recommend against using the eval method and instead use the method Ionut G. Stan posted above. I know it's more complicated, but each time you run eval, PHP loads the compiler engine all over again, and so it has a high overhead cost. You'll get a major performance increase (around 10x) if you use the function dispatch approach Ionut showed. Take a look at the comments on the eval function in the PHP manual and you'll see other people who have also been saying this: http://www.php.net/eval

I was once using eval hoping it would enable me to construct a fast templating mechanism for a web application, but calls to eval were very slow, and when I realised that eval was causing it I switched to a different approach. The speed gains were phenomenal.

Ray Hidayat