Что такое автозагрузка; Как вы используете spl_autoload, __autoload и spl_autoload_register?

Я изучаю передовые стандарты PHP и пытаюсь внедрять новые и полезные методы. Раньше я использовал __autoload, чтобы убежать, включая несколько файлов на каждой странице, но недавно я видел подсказку __autoload manual

spl_autoload_register() предоставляет более гибкую альтернативу для автозагрузка классов. По этой причине использование __ autoload()обескуражен и может быть устаревшим или удаленным в будущем.

но я действительно не могу понять, как реализовать spl_autoload и spl_autoload_register

Ответ 1

spl_autoload_register() позволяет вам зарегистрировать несколько функций (или статических методов из вашего собственного класса автозагрузки), которые PHP поместит в стек/очередь и будет вызывать последовательно при объявлении "нового класса".

Так, например:

spl_autoload_register('myAutoloader');

function myAutoloader($className)
{
    $path = '/path/to/class/';

    include $path.$className.'.php';
}

//-------------------------------------

$myClass = new MyClass();

В приведенном выше примере "MyClass" - это имя класса, который вы пытаетесь создать, PHP передает это имя как строку в spl_autoload_register(), которая позволяет вам выбрать переменную и использовать ее для "включения" соответствующего класс/файл. В результате вам не нужно специально включать этот класс с помощью оператора include/require...

Просто вызовите класс, для которого вы хотите создать экземпляр, как в примере выше, и, поскольку вы зарегистрировали собственную функцию (через spl_autoload_register()), которая будет выяснять, где находится весь ваш класс, PHP будет использовать эту функцию.

Преимущество использования spl_autoload_register() состоит в том, что в отличие от __autoload() вам не нужно реализовывать функцию автозагрузки в каждом __autoload() вами файле. spl_autoload_register() также позволяет зарегистрировать несколько функций автозагрузки, чтобы ускорить автозагрузку и сделать ее еще проще.

Пример:

spl_autoload_register('MyAutoloader::ClassLoader');
spl_autoload_register('MyAutoloader::LibraryLoader');
spl_autoload_register('MyAutoloader::HelperLoader');
spl_autoload_register('MyAutoloader::DatabaseLoader');

class MyAutoloader
{
    public static function ClassLoader($className)
    {
         //your loading logic here
    }


    public static function LibraryLoader($className)
    {
         //your loading logic here
    }

Что касается spl_autoload, руководство заявляет:

Эта функция предназначена для использования в качестве реализации по умолчанию для __autoload(). Если ничего не указано, и spl_autoload_register() вызывается без каких-либо параметров, то эти функции будут использоваться для любого последующего вызова __autoload().

С практической точки зрения, если все ваши файлы расположены в одном каталоге, а ваше приложение использует не только файлы .php, но и пользовательские файлы конфигурации, например, с расширениями .inc, то одной из стратегий, которую вы могли бы использовать, было бы добавление каталога, содержащего все файлы в PHP включают путь (через set_include_path()).
И поскольку вам также требуются ваши файлы конфигурации, вы должны использовать spl_autoload_extensions() чтобы перечислить расширения, которые вы хотите, чтобы PHP искал.

Пример:

set_include_path(get_include_path().PATH_SEPARATOR.'path/to/my/directory/');
spl_autoload_extensions('.php, .inc');
spl_autoload_register();

Поскольку spl_autoload является реализацией магического метода __autoload() по умолчанию, PHP вызовет spl_autoload, когда вы попытаетесь создать новый класс.

Надеюсь это поможет...

Ответ 2

Начиная с PHP 5.3, вы можете использовать spl_autoload_register() с пространствами имен, что означает, что вы можете организовать свой проект и автоматически загружать свои php-классы без каких-либо требований или включать и не переопределять функцию __autoload().

Чтобы продемонстрировать это поведение, просто создайте файл index.php:

<?php
spl_autoload_register();
var_dump(new Main\Application);

Затем создайте папку с именем Main, расположенную рядом с файлом index.php. Наконец, создайте файл под названием Application.php, расположенный в Main, и вставьте в него следующий код:

<?php namespace Main;
class Application{}

Ответ 3

Вот как я использую автозагрузку. В данном примере я хочу загрузить классы из 3 разных каталогов.

function namespaceAutoload($rawClass){

$class = str_replace('\\', DIRECTORY_SEPARATOR, $rawClass);

$possiblePaths[] = '..\sys\class\file.php';
$possiblePaths[] = '..\sys\class\lib\file.php';
$possiblePaths[] = '..\sys\class\class.file.inc.php';

foreach ($possiblePaths as $templatePath) {
    $path = str_replace(["\\", "file"], [DIRECTORY_SEPARATOR, $class], $templatePath);
    if (file_exists($path)) {
        require_once "$path";
        break;
    }
} spl_autoload_register("namespaceAutoload"); 

В приведенном примере PHP будет искать пространство имен \class в этих трех каталогах, используя эти три различных формата файлов.