It is possible to make accessible a Class within spl_autoload_register
(automatically)?
For example, I using spl_autoload_register
in index.php:
<?php
class Utils {
public function example() {
echo 'Hello word!';
}
}
spl_autoload_register(function($class)
{
$relative_class = strtolower(str_replace('\\', '/', $class));
$file = './src/' . $relative_class . '.php';
if (is_file($file)) {
require_once $file;
}
});
$user = new \Controllers\Foo\User;
This new \\Controllers\\Foo\\User;
autoload this file ./src/controllers/foo/user.php
user.php:
<?php
namespace Controllers/Foo;
class User
{
public function foo() {
//Something...
}
}
If I need to use a Utils class I'll have to add new \\Controllers\\Foo\\User
in the file user.php like this:
public function foo() {
\Utils::example();
}
or
<?php
namespace Controllers/Foo;
use \Utils as Utils;
class User
{
public function foo() {
Utils::example();
}
}
It is possible to make accessible to Utils class within spl_autoload_register
(automatically)? I would use without use \\Utils as Utils;
and without backslash ( \\Utils::
).
You can't. That's the whole point of using namespaces. You can reference a class whitout backslash or use
statement only if it is in the same namespace you are using it. You can't hack the autoloader to automagically import the target class into the current namespace changing its namespace on the fly.
If your class doesn't belong to a named namespace, then it is in the global namespace and you still have to use with \\
or use
. The same for import
or use
keywords in python, java, go, .net, c/c++, etc.
There is no standard anything to do this besides using use ... as ...
or "backslash" ( \\
), however we can "cheat the PHP" using eval()
within the spl_autoload_register()
to extend the Utils class within the namespace
.
Only use this if really necessary, prefer to use "backslash" (
\\
) oruse \\Utils as Utils
Example (read comments in code):
<?php
class Utils {
public static function example() {
echo 'Hello World!';
}
}
spl_autoload_register(function($class)
{
$relative_class = strtolower(str_replace('\\', '/', $class));
$file = './src/' . $relative_class . '.php';
if (is_file($file)) {
$np = explode('\\', $class); //Dividi string
//Check if class exists in namespace (prevent conflicts)
if (class_exists(implode('::', $np)) === false) {
//Remove "class name", use only "namespace"
array_pop($np);
//evaluate a namespace in eval (extends the Utils class)
eval(
'namespace ' . implode('\\', $np) . ' {' . PHP_EOL .
'class Utils extends \Utils {}' . PHP_EOL .
'}'
);
}
require_once $file;
}
});
$user = new \Controllers\Foo\User;
$user->foo(); //Show "Hello word!"
I admit that it is an ugly hack and maybe I will not use, but it's still a hint yes.
Note:
use \\Utils as Utils
not work ineval
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.