#php #oop #cakephp #namespaces #cakephp-3.0
#php #ооп #cakephp #пространства имен #cakephp-3.0
Вопрос:
Я создал класс в папке контроллера проекта Cake следующим образом:
<?php
class Hi
{
function __construct(){ }
public function hi()
{
echo "hi!";
exit;
}
}
Затем в контроллере я попытался включить его:
<?php
namespace AppController;
use AppControllerAppController;
include_once "Hi.php";
class MyController extends AppController
{
public function sayHi()
{
$a = new Hi();
$a.hi();
}
}
Вот ошибка, с которой я сталкиваюсь:
Неустранимая ошибка: не удается объявить класс Hi, поскольку имя уже используется в pathapisrcControllerHi.php в строке 2
Что происходит?
MyController.php
и Hi.php
находятся в той же папке. Я использую PHP 7.
Комментарии:
1. Не знаю, но что это
$a.hi();
???2. Это просто для тестирования…
3. Теперь я понял, хахахах… Это
$a->hi();
Ответ №1:
Включение файла не сделает классы в этом файле частью текущего пространства имен, поскольку пространства имен — это функциональность для каждого файла.
http://php.net/…namespaces.importing.php#language.namespaces.importing.scope
Ваш Hi
класс будет объявлен в глобальном пространстве имен, и ваш new Hi()
заставит PHP искать его в текущем пространстве имен, т. Е. Он будет искать то AppControllerHi
, чего не существует, поэтому запускается автозагрузчик composer и сопоставит это с помощью префикса пространства имен PSR-4, совпадающего с src/Controller/Hi.php
, который будет включатьснова файл, и вот тогда это происходит.
http://www.php-fig.org/psr/psr-4/
Короче говоря, хотя использование new Hi()
исправит это, вам лучше не включать файлы классов вручную или объявлять их в путях, где они не принадлежат. Вместо этого объявляйте свои файлы и классы надлежащим образом, совместимым с автозагрузкой, то есть, например, с соответствующим пространством имен в пути, который соответствует этому пространству имен, например
namespace AppUtils;
class Hi {
// ...
}
в
src/Utils/Hi.php