1

I often pass local variables to functions declared in variables like:

public function getTotal($tax)
{
    $total = 0.00;

    $callback =
        /* This line here: */
        function ($quantity, $product) use ($tax, &$total)
        {
            $pricePerItem = constant(__CLASS__ . "::PRICE_" .
                strtoupper($product));
            $total += ($pricePerItem * $quantity) * ($tax + 1.0);
        };

    array_walk($this->products, $callback);
    return round($total, 2);
}

Is it possible to pass every local variable that is declared in the same scope as declared function without listing them all like use($a,$b,$c ...)?

So if I would like like use(*) everything that was accessable in parent scope will be passed to declared function scope?

4
  • You use improper approach. Since you use OOP you can define needed callback as a method of the same class and then you can pass all needed data through class properties. Commented Aug 20, 2014 at 14:07
  • @hindmost I was about to suggest the same, but I realized for a local use case, such as walking an array. The fact the method would need to be public to pass as a callback would prove to be clutter. Commented Aug 20, 2014 at 14:11
  • @Flosculus That's not right. The fact that the method only must be public if it used/called outside of its class (object). Otherwise it might have any level of visibility, i.e. it can be protected or even private. Commented Aug 20, 2014 at 14:43
  • @hindmost This is true, and very useful :P Commented Sep 9, 2014 at 8:13

4 Answers 4

2

get_defined_vars could do the job for you

$a = 1;

function test ($c) {
  $b = 2;
  var_dump(get_defined_vars()); // var_dump for the generic example, adapt as you need for use
}

test(3);

// array(2) { ["c"]=> int(3) ["b"]=> int(2) } 

You will have to use these vars from an array though.

Sign up to request clarification or add additional context in comments.

2 Comments

But in another function, there will be no local variables from previous function
@Justinas OP is looking for local variables declared in the same scope, not for all the variables
1

Closures should be very limited in what they do. 4-5 lines tops really.

In my mind, it is far better to define the variables being made available to it as closures are essentially unstructured.

I usually inline them like this though:

array_walk($this->products, function ($quantity, $product) use ($tax, &$total) {

});

The new operation of the use keyword might be a bit cumbersome, but it is better than global. This is a much more manageable can of worms.

Comments

0

No, you have to list all variables, that you pass to function. You can add them to some array and pass as single argument. But you can use func_get_args to get all variables, passed to function and not list all of them in function header.

Comments

0

You can use get_defined_vars and extract.

$a = 1;
$b = 2;

$vars = get_defined_vars();

(function () use ($vars)
{
    extract($vars);
    
    echo $a; // Outputs 1
    echo $b; // Outputs 2
})();

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.