Asked  7 Months ago    Answers:  5   Viewed   39 times

According to the most programming languages scope rules, I can access variables that are defined outside of functions inside them, but why doesn't this code work?

<?php
    $data = 'My data';

    function menugen() {
        echo "[" . $data . "]";
    }

    menugen();
?>

The output is [].

 Answers

60

It is not working because you have to declare which global variables you'll be accessing:

$data = 'My data';

function menugen() {
    global $data; // <-- Add this line

    echo "[" . $data . "]";
}

menugen();

Otherwise you can access it as $GLOBALS['data']. See Variable scope.

Even if a little off-topic, I'd suggest you avoid using globals at all and prefer passing as parameters.

Wednesday, March 31, 2021
 
The_Perfect_Username
answered 7 Months ago
94

PHP<5.3 does not support closures, so you'd have to either pass $foo to inner() or make $foo global from within both outer() and inner() (BAD).

In PHP 5.3, you can do

function outer()
{
  $foo = "...";
  $inner = function() use ($foo)
  {
    print $foo;
  };
  $inner();
}
outer();
outer();
Wednesday, March 31, 2021
 
laurent
answered 7 Months ago
60

There is an important difference between your two examples:

$global_variable = 1;

$closure = function() use ($global_variable) {
    return $global_variable; 
};

$closure2 = function() {
    global $global_variable;
    return $global_variable;
};

$global_variable = 99;

echo $closure();    // this will show 1
echo $closure2();   // this will show 99 

use takes the value of $global_variable during the definition of the closure while global takes the current value of $global_variable during execution.

global inherits variables from the global scope while use inherits them from the parent scope.

Saturday, May 29, 2021
 
felipsmartins
answered 5 Months ago
67

You need to specify which variables should be closed in this way:

function($row) use ($pid) { ... }
Tuesday, August 10, 2021
 
Johnson
answered 3 Months ago
43

Because it is in another scope. If you want to use $wrap, try:

function($val) use ($wrap){
   //etc
}

Of course, your function here doesn't need a callback:

return $wrap.implode($wrap.$delim.$wrap,$ar).$wrap;
Friday, August 13, 2021
 
Anass Kartit
answered 3 Months ago
Only authorized users can answer the question. Please sign in first, or register a free account.
Not the answer you're looking for? Browse other questions tagged :