在 PHP 中的 class 方法中包含 class 文件时,范围是否会发生变化?
Does scope change at all when including class files in a class method in PHP?
我觉得这个问题很愚蠢,但我可以向专家咨询一下 class 方法中包含的行为吗?
当我使用 require_once
在 class 方法中包含 class 定义文件时,是否有任何我需要注意的问题。我正在考虑工厂 class 上的自动加载方法,但实际上任何时候该方法确实包含或需要。
我的期望是,它应该与我在开始时将它们简单地包含在一个包含文件中一样。我对吗?我只问当你在 class 方法中包含一个文件时它继承了方法范围。
需要注意的一件事是全局变量的作用域。例如:
文件:a.php
<?php
$foo = 'bar';
文件:b.php
<?php
require_once 'a.php';
echo $foo;
文件:c.php
<?php
load_foo();
show_foo();
function load_foo() {
require_once 'a.php';
}
function show_foo() {
require_once 'b.php';
}
现在,如果您直接 运行 b.php
(例如 php b.php
),您将得到正确的输出:
bar
然而,如果你 运行 c.php
你会得到这个:
PHP Notice: Undefined variable: foo in C:\temp\b.php on line 3
PHP Stack trace:
PHP 1. {main}() C:\temp\c.php:0
PHP 2. show_foo() C:\temp\c.php:3
PHP 3. require_once() C:\temp\c.php:9
错误的原因是在 c.php
中我们在函数 load_foo()
中加载了 a.php
。这导致变量 $foo
被限定为函数 load_foo()
的 local 变量,否则它将是一个全局变量。然后,当 show_foo()
被调用时,它会加载 b.php
,它会跳过 require_once
(因为我们已经加载了 a.php
),然后尝试打印 $foo
。但它不能,因为 $foo
不再定义。当我们 load_foo()
退出时,它超出了范围。
因此,回到您最初的问题 - 如果您使用自动加载并且自动加载发生在 function/method 上下文中,则全局变量将在本地范围内,如上例所示。如果你绝对需要使用全局变量,请确保在定义它们之前使用 global
关键字(即 global $foo
作为上面 a.php
的第一行)和在你使用它们之前(同样,global $foo
在 b.php
中的 require_once
之后。
我觉得这个问题很愚蠢,但我可以向专家咨询一下 class 方法中包含的行为吗?
当我使用 require_once
在 class 方法中包含 class 定义文件时,是否有任何我需要注意的问题。我正在考虑工厂 class 上的自动加载方法,但实际上任何时候该方法确实包含或需要。
我的期望是,它应该与我在开始时将它们简单地包含在一个包含文件中一样。我对吗?我只问当你在 class 方法中包含一个文件时它继承了方法范围。
需要注意的一件事是全局变量的作用域。例如:
文件:a.php
<?php
$foo = 'bar';
文件:b.php
<?php
require_once 'a.php';
echo $foo;
文件:c.php
<?php
load_foo();
show_foo();
function load_foo() {
require_once 'a.php';
}
function show_foo() {
require_once 'b.php';
}
现在,如果您直接 运行 b.php
(例如 php b.php
),您将得到正确的输出:
bar
然而,如果你 运行 c.php
你会得到这个:
PHP Notice: Undefined variable: foo in C:\temp\b.php on line 3
PHP Stack trace:
PHP 1. {main}() C:\temp\c.php:0
PHP 2. show_foo() C:\temp\c.php:3
PHP 3. require_once() C:\temp\c.php:9
错误的原因是在 c.php
中我们在函数 load_foo()
中加载了 a.php
。这导致变量 $foo
被限定为函数 load_foo()
的 local 变量,否则它将是一个全局变量。然后,当 show_foo()
被调用时,它会加载 b.php
,它会跳过 require_once
(因为我们已经加载了 a.php
),然后尝试打印 $foo
。但它不能,因为 $foo
不再定义。当我们 load_foo()
退出时,它超出了范围。
因此,回到您最初的问题 - 如果您使用自动加载并且自动加载发生在 function/method 上下文中,则全局变量将在本地范围内,如上例所示。如果你绝对需要使用全局变量,请确保在定义它们之前使用 global
关键字(即 global $foo
作为上面 a.php
的第一行)和在你使用它们之前(同样,global $foo
在 b.php
中的 require_once
之后。