索引中定义的变量不可访问
Variable defined in index not accessible
我有一个 php 框架,我在其中通过索引文件路由所有请求。在索引文件中我有:
index.php
$module = new module();
$module->SetName("user");
$call = new call();
$call->SetController("login");
然后我进行一些处理以找到请求的控制器文件。一旦找到,我就会
$call->LoadController()
此方法需要模块指定的文件并调用。在这种情况下它会做
require_once CONTROLLERS . "user/"."login.php"
到目前为止一切都很好。在我加载的控制器文件中
controllers/user/login.php
$call->SetView("login")
我得到一个 php 错误
undefined variable $call
我不知道为什么?
原因是,通过 including/requiring 一个文件,您的变量范围与您预期的正好相反。有关详细信息,请查看 PHP Documentation
这里有一个例子,非常清楚:
vars.php
<?php
$color = 'green';
$fruit = 'apple';
?>
test.php
<?php
echo "A $color $fruit"; // A
include 'vars.php';
echo "A $color $fruit"; // A green apple
?>
$call 在 LoadController() 内部是未知的,因为它在全局范围内。包含的控制器文件共享 LoadController 的范围。这就是为什么不能在控制器文件中使用 $call 的原因。
有以下三种解决方案:
您可以在 LoadController() 中使用 "global" 关键字,因此 $call 在 LoadController() 和包含的控制器文件中是已知的:
class module
{
public function LoadController()
{
global $call;
require_once('controllers/user/login.php');
}
}
但是这个解决方案很丑。
第二种解决方案是在包含的控制器文件中使用 $this->SetView() 而不是 $call->SetView() 。此解决方案的缺点是您在包含的文件中有多个 $this,并且您不知道 class 对 $this 意味着什么。仍然比第一个解决方案更好。
第三种解决方案是使用单例模式。你只需要class模块的一个对象,它会为你避免很多麻烦。然后您可以从任何您想要的地方调用 SetView(),而不会出现全局变量和未知范围的问题。您可以这样调用 SetView():module::getInstance()->SetView()。查看单例模式:https://duckduckgo.com/?q=singleton+pattern
我有一个 php 框架,我在其中通过索引文件路由所有请求。在索引文件中我有:
index.php
$module = new module();
$module->SetName("user");
$call = new call();
$call->SetController("login");
然后我进行一些处理以找到请求的控制器文件。一旦找到,我就会
$call->LoadController()
此方法需要模块指定的文件并调用。在这种情况下它会做
require_once CONTROLLERS . "user/"."login.php"
到目前为止一切都很好。在我加载的控制器文件中
controllers/user/login.php
$call->SetView("login")
我得到一个 php 错误
undefined variable $call
我不知道为什么?
原因是,通过 including/requiring 一个文件,您的变量范围与您预期的正好相反。有关详细信息,请查看 PHP Documentation
这里有一个例子,非常清楚:
vars.php
<?php
$color = 'green';
$fruit = 'apple';
?>
test.php
<?php
echo "A $color $fruit"; // A
include 'vars.php';
echo "A $color $fruit"; // A green apple
?>
$call 在 LoadController() 内部是未知的,因为它在全局范围内。包含的控制器文件共享 LoadController 的范围。这就是为什么不能在控制器文件中使用 $call 的原因。 有以下三种解决方案: 您可以在 LoadController() 中使用 "global" 关键字,因此 $call 在 LoadController() 和包含的控制器文件中是已知的:
class module
{
public function LoadController()
{
global $call;
require_once('controllers/user/login.php');
}
}
但是这个解决方案很丑。
第二种解决方案是在包含的控制器文件中使用 $this->SetView() 而不是 $call->SetView() 。此解决方案的缺点是您在包含的文件中有多个 $this,并且您不知道 class 对 $this 意味着什么。仍然比第一个解决方案更好。
第三种解决方案是使用单例模式。你只需要class模块的一个对象,它会为你避免很多麻烦。然后您可以从任何您想要的地方调用 SetView(),而不会出现全局变量和未知范围的问题。您可以这样调用 SetView():module::getInstance()->SetView()。查看单例模式:https://duckduckgo.com/?q=singleton+pattern