Большинство разработчиков объектно-ориентированных приложений используют такое соглашение именования файлов, в котором каждый класс хранится в отдельно созданном для него файле. Одной из наиболее при этом досаждающих деталей является необходимость писать в начале каждого скрипта длинный список подгружаемых файлов.
В PHP 5 это делать не обязательно. Можно определить функцию __autoload(), которая будет автоматически вызвана при использовании ранее неопределенного класса или интерфейса. Вызов этой функции - последний шанс для интерпретатора загрузить класс прежде, чем он закончит выполнение скрипта с ошибкой.
spl_autoload_register() предоставляет более гибкую альтернативу для автоматической загрузки классов. По этой причине использовать __autoload() не рекомендуется, а сама функция в будущем может перестать поддерживаться или быть удалена.
Замечание:
До версии 5.3.0, исключения, вызванные в функции __autoload, не могли быть перехвачены в блоке catch и завершались с неисправимой ошибкой. Начиная с версии 5.3.0 эти исключения можно перехватывать в ближайшем блоке catch. Если бросить определенное пользователем исключение, то класс этого исключения должен быть доступен. Функция __autoload также может использоваться рекурсивно для автоматической загрузки пользовательских классов исключений.
Замечание:
Автоматическая загрузка недоступна в случае использования PHP в командной строке в интерактивном режиме.
Замечание:
Если имя класса используется, например, для вызова через call_user_func(), то оно может содержать некоторые опасные символы, такие как ../. Поэтому, рекомендуется не использовать данные от пользователей в таких функциях или же, как минимум, проверять значения в __autoload().
Пример #1 Пример автоматической загрузки
В этом примере функция пытается загрузить классы MyClass1 и MyClass2 из файлов MyClass1.php и MyClass2.php соответственно.
<?php
function __autoload($class_name) {
include $class_name . '.php';
}
$obj = new MyClass1();
$obj2 = new MyClass2();
?>
Пример #2 Еще один пример автоматической загрузки
В этом примере представлена попытка загрузки интерфейса ITest.
<?php
function __autoload($name) {
var_dump($name);
}
class Foo implements ITest {
}
/*
string(5) "ITest"
Fatal error: Interface 'ITest' not found in ...
*/
?>
Пример #3 Автоматическая загрузка с перехватом исключения в версиях 5.3.0+
В данном примере вызывается исключение и отлавливается блоком try/catch.
<?php
function __autoload($name) {
echo "Want to load $name.\n";
throw new Exception("Unable to load $name.");
}
try {
$obj = new NonLoadableClass();
} catch (Exception $e) {
echo $e->getMessage(), "\n";
}
?>
Результат выполнения данного примера:
Want to load NonLoadableClass. Unable to load NonLoadableClass.
Пример #4 Автоматическая загрузка с перехватом исключения в версиях 5.3.0+ - Класс пользовательского исключения не подгружен
В данном примере вызывается недоступное исключение.
<?php
function __autoload($name) {
echo "Want to load $name.\n";
throw new MissingException("Unable to load $name.");
}
try {
$obj = new NonLoadableClass();
} catch (Exception $e) {
echo $e->getMessage(), "\n";
}
?>
Результат выполнения данного примера:
Want to load NonLoadableClass. Want to load MissingException. Fatal error: Class 'MissingException' not found in testMissingException.php on line 4