Подробное объяснение API отражения PHP

API отражения в PHP похож на пакет java.lang.reflect в Java. Он состоит из ряда встроенных классов, которые могут анализировать свойства, методы и классы. В некоторых отношениях она похожа на объектные функции, такие как get_class_vars(), но более гибкая и может предоставить больше информации. API отражения также работает с последними объектно-ориентированными функциями PHP, такими как управление доступом, интерфейсы и абстрактные классы. Старые функции класса не так просты в использовании с этими новыми функциями. Друзья, которые видели исходный код фреймворка, должны иметь определенное представление о механизме отражения PHP, таком как внедрение зависимостей, пул объектов, загрузка классов, некоторые шаблоны проектирования и т. д., все используют механизм отражения.

Частичные классы API отражения

Используя эти классы в Reflection API, можно получить доступ к расширенной информации об объектах, функциях и сценариях во время выполнения. Эту информацию можно использовать для анализа классов или построения фреймворков.

добрый описывать
Отражение Предоставляет статическую функцию export() для получения сводной информации о классе.
Класс отражения Информация о классе и инструменты
ОтражениеМетод Информация о методе класса и инструменты
ОтражениеПараметр Информация о параметрах метода
ОтражениеСвойство информация об атрибутах класса
ОтражениеФункция Информация о функциях и инструменты
ОтражениеРасширение Информация о расширении PHP
Исключение отражения класс ошибки

Получить информацию о классе

В нашей работе мы использовали некоторые функции для проверки атрибутов класса, например: get_class_methods, getProduct и т.д. Эти методы имеют большие ограничения для получения подробной информации о классе.

Мы можем получить информацию о классе через класс API отражения: экспорт статического метода, предоставляемый Reflection и ReflectionClass, экспорт может предоставить почти всю информацию о классе, включая статус контроля доступа к атрибутам и методам, параметры, необходимые для каждого метода, и каждый Позиция метода в документе скрипта. Вывод статического метода экспорта этих двух классов инструментов одинаков, но использование отличается.

Сначала создайте простой класс

<?php

класс Студент {
    общественное имя $;
    защищенный возраст;
    частный секс;

    публичная функция __construct($name, $age, $sex)
    {
        $this->setName($name);
        $this->setAge($age);
        $this->setSex($sex);
    }

    общедоступная функция setName($name)
    {
       $это->имя = $имя;
    }

    защищенная функция setAge($age)
    {
        $this->age = $возраст;
    }

    приватная функция setSex($sex)
    {
        $this->sex = $sex;
    }
}

Используйте ReflectionClass::export() для получения информации о классе

ReflectionClass::export('Студент');

Распечатать результат:

 Вывод ReflectionClass::export()

Класс ReflectionClass предоставляет множество инструментов и методов, список которых в официальном руководстве выглядит следующим образом:

 Класс отражения

Используйте Reflection::export() для получения информации о классе 

$prodClass = новый ReflectionClass('Студент');
Отражение:: экспорт ($ prodClass);

распечатать результат

 Вывод Reflection::export()

После создания объекта ReflectionClass вы можете использовать класс инструментов Reflection для вывода соответствующей информации класса Student. Reflection::export() может форматировать и экспортировать экземпляр любого класса, реализующего интерфейс Reflector.

проверить класс

Инструментальный класс ReflectionClass, который мы изучили ранее, знает, что этот класс предоставляет множество инструментальных методов для получения информации о классе. Например, мы можем получить тип класса Student, можно ли его инстанцировать

Функция инструмента

функция classData(ReflectionClass $class) {
    $детали = '';
    $name = $class->getName(); // возвращает имя класса для проверки
    if ($class->isUserDefined()) { // проверяем, определен ли класс пользователем
        $details .= "$имя определяется пользователем" . PHP_EOL;
    }
    if ($class->isInternal()) { // проверяем, определен ли класс внутри расширения или ядра
        $details .= "$имя встроено" . PHP_EOL;
    }
    if ($class->isInterface()) { // проверяем, является ли класс интерфейсом
        $details .= "$name — интерфейс" . PHP_EOL;
    }
    if ($class->isAbstract()) { // проверяем, является ли класс абстрактным
        $details .= "$name является абстрактным классом" . PHP_EOL;
    }
    if ($class->isFinal()) { // проверяем, объявлен ли класс окончательным
        $details .= "$name — конечный класс" . PHP_EOL;
    }
    if ($class->isInstantiable()) { // проверяем, можно ли создать экземпляр класса
        $details .= "$name может быть создано" . PHP_EOL;
    } еще {
        $details .= "Невозможно создать экземпляр $name" . PHP_EOL;
    }
    вернуть $детали;
}

$prodClass = новый ReflectionClass('Студент');
распечатать данные класса ($ prodClass);

распечатать результат

Студент определяется пользователем
Студент может быть создан

В дополнение к получению соответствующей информации о классе вы также можете получить соответствующую информацию об исходном коде, такую ​​как имя файла пользовательского класса и начальную и конечную строки класса в файле, предоставленном объектом ReflectionClass.

функция getClassSource (ReflectionClass $ class) {
    $path = $class->getFileName(); // Получить абсолютный путь к файлу класса
    $lines = @file($path); // Получить массив всех строк в файле
    $from = $class->getStartLine(); // Указываем начальную строку класса
    $to = $class->getEndLine(); // Указываем конечную строку класса
    $len = $to - $from + 1;
    return implode(array_slice($lines, $from - 1, $len));
}

$prodClass = новый ReflectionClass('Студент');
var_dump (getClassSource ($ prodClass));

распечатать результат
строка 'класс Студент {
    общественное имя $;
    защищенный возраст;
    частный секс;

    публичная функция __construct($name, $age, $sex)
    {
        $this->setName($name);
        $this->setAge($age);
        $this->setSex($sex);
    }

    общедоступная функция setName($name)
    {
        $это->имя = $имя;
    }

    защищенная функция setAge($age)
    {
        $this->age = $возраст;
    }

    приватная функция setSex($sex)
    {
        $this->sex = $sex;
    }
}
' (длина = 486)

Мы видим, что getClassSource принимает в качестве параметра объект ReflectionClass и возвращает исходный код соответствующего класса. Эта функция игнорирует обработку ошибок, на практике следует проверять аргументы и коды результатов!

Метод проверки

Подобно проверке классов, объекты ReflectionMethod можно использовать для проверки методов в классах.

Есть два способа получить объект ReflectionMethod:

Первый — получить массив объектов ReflectionMethod через ReflectionClass::getMethods() Преимущество этого метода в том, что ему не нужно заранее знать имя метода, и он вернет объекты ReflectionMethod всех методов в классе. .

Во-вторых, создать экземпляр объекта напрямую с помощью класса ReflectionMethod.Таким образом, можно получить только один объект метода класса, а имя метода должно быть известно заранее.

Служебные методы для объектов ReflectionMethod:

 ОтражениеМетод

ReflectionClass::getMethods()

Мы можем получить массив объектов ReflectionMethod через ReflectionClass::getMethods().

$prodClass = новый ReflectionClass('Студент');
$methods = $prodClass->getMethods();
var_dump ($ методы);

распечатать результат

массив (размер=4)
  0 => &
    объект (ReflectionMethod) [2]
      public 'name' => string '__construct' (длина = 11)
      public 'class' => string 'Студент' (длина = 7)
  1 => &
    объект (метод отражения) [3]
      public 'name' => строка 'setName' (длина = 7)
      public 'class' => string 'Студент' (длина = 7)
  2 => &
    объект (метод отражения) [4]
      public 'name' => string 'setAge' (длина = 6)
      public 'class' => string 'Студент' (длина = 7)
  3 => &
    объект (метод отражения) [5]
      public 'name' => string 'setSex' (длина = 6)
      public 'class' => string 'Студент' (длина = 7)

Видно, что мы получили массив объектов Student's ReflectionMethod, каждый элемент — это объект, который имеет два публичных свойства, name — имя метода, а class — класс, которому он принадлежит. Мы можем вызывать методы объекта для получения информации о методе.

ОтражениеМетод

Напрямую используйте класс ReflectionMethod для получения информации о методах класса.

$method = новый ReflectionMethod('Студент', 'setName');
var_dump ($ метод);

распечатать результат

объект (ReflectionMethod) [1]
  public 'name' => строка 'setName' (длина = 7)
  public 'class' => string 'Студент' (длина = 7)

Уведомление

В PHP5 ReflectionMethod::retursReference() не вернет true, если проверяемый метод возвращает только объекты (даже если объекты присваиваются или передаются по ссылке). ReflectionMethod::returnsReference() возвращает значение true, только если проверяемый метод был явно объявлен для возврата ссылок (с символом & перед именем метода).

Проверить параметры метода

В PHP5 при объявлении метода класса можно ограничить тип объекта в параметре, поэтому возникает необходимость проверять параметры метода.

Подобно проверке методов, объект ReflectionParameter может использоваться для проверки методов в классе.Этот объект может сообщить вам имя параметра, может ли переменная быть передана по ссылке, а также сообщить вам о подсказках типа параметра и о том, является ли метод принимает нулевые значения в качестве параметров.

Есть также два способа получения объектов ReflectionParameter, которые очень похожи на получение объектов ReflectionMethod:

Первый — вернуть массив объектов ReflectionParameter с помощью метода ReflectionMethod::getParameters(), который может получить все объекты параметров метода.

Второй — напрямую использовать класс ReflectionParameter для создания экземпляров и получения объектов.Этот метод может получать объекты только с одним параметром.

Вспомогательные методы для объектов ReflectionParameter:

 ОтражениеПараметр

ReflectionMethod::getParameters()

Как и метод get, этот метод возвращает массив, содержащий объекты ReflectionParameter для каждого параметра метода.

$method = новый ReflectionMethod('Студент', 'setName');
$params = $method->getParameters();
var_dump ($ параметры);

распечатать результат

массив (размер=1)
  0 => &
    объект (параметр отражения) [2]
      public 'name' => строка 'name' (длина = 4)

ОтражениеПараметр

Давайте посмотрим на этот метод.Для лучшего понимания я модифицирую метод setName класса Student и добавляю два параметра a, b

...
    общедоступная функция setName($name, $a, $b)
    {
        $это->имя = $имя;
    }
...

Во-первых, давайте посмотрим на метод построения класса ReflectionParameter.

public ReflectionParameter::__construct (строка $функция, строка $параметр)

Вы можете видеть, что класс получает два параметра при создании экземпляра:

$функция: когда вам нужно получить функцию как общедоступную, вам нужно только передать имя функции. Когда функция является методом класса, необходимо передать массив в формате: массив('класс', 'функция').

$parameter: этот параметр можно передать двумя способами: первый — это имя параметра (без символа $), а второй — индекс параметра. Примечание. Будь то имя параметра или индекс, параметр должен существовать, иначе будет сообщено об ошибке.

Вот пример:

$params = new ReflectionParameter(array('Студент', 'setName'), 1);
var_dump ($ параметры);

распечатать результат

объект (параметр отражения) [1]
  public 'name' => строка 'a' (длина = 1)

Давайте определим другую функцию для тестирования

функция foo($a, $b, $c) { }
$reflect = новый параметр отражения ('foo', 'c');
var_dump ($ отражение);

распечатать результат

объект (параметр отражения) [2]
  public 'name' => строка 'c' (длина = 1)

эпилог

API отражения PHP очень мощный, он может получить подробную информацию о классе. Мы можем написать класс через API отражения для динамического вызова объекта Module, который может свободно загружать сторонние плагины и интегрировать их в существующие системы. Нет необходимости жестко встраивать сторонний код в исходный код. Хотя использование отражения в реальной разработке относительно невелико, понимание API отражения очень полезно для понимания структуры кода и разработки бизнес-моделей в работе. Этот пост в блоге писался с перерывами в течение длительного времени (в основном из-за лени!), если есть какие-то ошибки и недочеты, прошу меня поправить и подсказать! !

Supongo que te gusta

Origin blog.csdn.net/Api_k/article/details/132120239
Recomendado
Clasificación