PHP 全局变量的作用域与使用方式
在使用PHP开发时,全局变量的行为与其他语言(如C++、Java)存在显著差异。本文将深入探讨PHP中全局变量的定义方式和作用域规则。
全局变量的基本使用
考虑以下场景:我们需要在一个函数内部修改外部定义的变量值:
<?php
$username = "admin";
function updateUsername(){
$username = "guest";
}
updateUsername();
echo "当前用户:" . $username . "<br/>";
?>
执行后输出结果为:当前用户:admin。这并非预期的"guest",原因是函数体内的$username被解析为局部变量,其作用范围仅限于函数内部。
为解决此问题,需要使用global关键字声明外部变量:
<?php
global $username;
$username = "admin";
function updateUsername(){
$username = "guest";
}
updateUsername();
echo "当前用户:" . $username . "<br/>";
?>
注意:不能同时声明并赋值全局变量,如global $username = "admin"的写法是错误的。
然而上述代码执行后结果仍为"admin"。这说明global的正确用法是:在函数内部声明需要引用的外部变量,使其相当于通过参数传入。以下是正确的使用方式:
<?php
$username = "admin";
function updateUsername(){
global $username;
$username = "guest";
}
updateUsername();
echo "当前用户:" . $username . "<br/>";
?>
执行结果为:当前用户:guest。这表明global的作用相当于引用传递参数,而非将变量作用域改为全局。
再来看一个例子:
<?php
$username = "admin";
function updateUsername(){
global $username;
$username = "guest";
}
function resetUsername(){
$username = "root";
}
updateUsername();
resetUsername();
echo "当前用户:" . $username . "<br/>";
?>
输出结果为:当前用户:guest。如果在resetUsername()中添加global $username声明,则输出变为:当前用户:root。
使用$GLOBALS超全局变量
除global关键字外,还可以使用超全局变量$GLOBALS访问全局变量:
<?php
$username = "admin";
function updateUsername(){
$GLOBALS['username'] = "guest";
}
updateUsername();
echo "当前用户:" . $username . "<br/>";
?>
global与$GLOBALS的区别
通过以下示例说明二者的差异:
<?php
$a = 1;
$b = 2;
function test1(){
$GLOBALS['b'] = &$GLOBALS['a'];
}
test1();
echo $b . "<br />";
$c = 1;
$d = 2;
function test2(){
global $c, $d;
$d = &$c;
}
test2();
echo $d . "<br />";
?>
输出结果:$b的值为1,$d的值为2。原因是$GLOBALS['c']是外部全局变量本身,而global $c是外部变量的同名引用。这意味着$GLOBALS在整个脚本作用域内都可用,在函数或方法中无需执行global $variable即可访问。$GLOBALS与其他超全局变量不同,在PHP中始终可用。
再看另一个例子:
<?php
$val1 = 100;
function test1(){
unset($GLOBALS['val1']);
}
test1();
echo isset($val1) ? $val1 : "val1不存在" . "<br />";
$val2 = 100;
function test2(){
global $val2;
unset($val2);
}
test2();
echo $val2 . "<br />";
?>
输出结果:val1不存在,而$val2的值为100。这证明使用global声明的变量仅是别名引用,原始变量的值并未改变。实际上,global $var等价于$var = &$GLOBALS['var'],它仅是对外部变量的一种引用方式。