Проверка, реализует ли класс экземпляра интерфейс?



учитывая экземпляр класса, можно ли определить, реализует ли он определенный интерфейс? Насколько я знаю, нет встроенной функции, чтобы сделать это напрямую. Какие варианты у меня есть (если есть)?

653   5  

5 ответов:

interface IInterface
{
}

class TheClass implements IInterface
{
}

$cls = new TheClass();
if ($cls instanceof IInterface) {
    echo "yes";
}

вы можете использовать "оператор instanceof оператор". Чтобы использовать его, левый операнд является экземпляром класса, а правый операнд-интерфейсом. Она возвращает true, если объект реализует определенный интерфейс.

как therefromhere указывает, что вы можете использовать class_implements(). Как и в случае с отражением, этого позволяет указать имя класса в виде строки и не требует экземпляра класса:

interface IInterface
{
}

class TheClass implements IInterface
{
}

$interfaces = class_implements('TheClass');

if (isset($interfaces['IInterface'])) {
    echo "Yes!";
}

class_implements() является частью расширения SPL.

см.:http://php.net/manual/en/function.class-implements.php

Тесты Производительности

некоторые простые тесты производительности показывают стоимость каждого подход:

учитывая экземпляр объекта

Object construction outside the loop (100,000 iterations)
 ____________________________________________
| class_implements | Reflection | instanceOf |
|------------------|------------|------------|
| 140 ms           | 290 ms     | 35 ms      |
'--------------------------------------------'

Object construction inside the loop (100,000 iterations)
 ____________________________________________
| class_implements | Reflection | instanceOf |
|------------------|------------|------------|
| 182 ms           | 340 ms     | 83 ms      | Cheap Constructor
| 431 ms           | 607 ms     | 338 ms     | Expensive Constructor
'--------------------------------------------'

дано только имя класса

100,000 iterations
 ____________________________________________
| class_implements | Reflection | instanceOf |
|------------------|------------|------------|
| 149 ms           | 295 ms     | N/A        |
'--------------------------------------------'

где дорогой _ _ construct () является:

public function __construct() {
    $tmp = array(
        'foo' => 'bar',
        'this' => 'that'
    );  

    $in = in_array('those', $tmp);
}

эти тесты основаны на этот простой код.

nlaq указывает, что instanceof можно использовать для проверки, является ли объект экземпляром класса, реализующего интерфейс.

но instanceof не различает тип класса и интерфейс. Вы не знаете, является ли объект класс это называется IInterface.

вы также можете использовать API отражения в PHP, чтобы проверить это более конкретно:

$class = new ReflectionClass('TheClass');
if ($class->implementsInterface('IInterface'))
{
  print "Yep!\n";
}

посмотреть http://php.net/manual/en/book.reflection.php

просто чтобы помочь будущим поискам is_subclass_of тоже хороший вариант (для PHP 5.3.7+):

if (is_subclass_of($my_class_instance, 'ISomeInterfaceName')){
    echo 'I can do it!';
}

вы также можете сделать следующее

public function yourMethod(YourInterface $objectSupposedToBeImplementing) {
   //.....
}

он выдаст восстанавливаемую ошибку, если $objectSupposedToBeImplementing не реализует YourInterface интерфейс.

Comments

    Ничего не найдено.