Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

php - check if class name stored in a string is implementing an interface

I understand that my question is somehow wrong, but I'm still trying to solve this problem.

I have an interface Programmer:

interface Programmer {     public function writeCode(); } 

and a couple of namespaced classes:

  • Students\BjarneProgrammer (implements Programmer)
  • Students\CharlieActor (implements Actor)

I have this class names stored in array $students = array("BjarneProgrammer", "CharlieActor");

I want to write a function, that will return an instance of class if it's implementing Programmer interface.

Examples:

getStudentObject($students[0]); - It should return an instance of BjarneProgrammer because it's implementing Programmer.

getStudentObject($students[1]); - It should return false because Charlie is not a Programmer.

I tried it using instanceof operator, but the main problem is that I do not want to instantiate an object if it's not implementing Programmer.

I checked How to load php code dynamically and check if classes implement interface, but there is no appropriate answer as I don't want to create object unless it's returned by function.

like image 907
Stichoza Avatar asked Nov 24 '13 00:11

Stichoza


People also ask

How do you check if a class is an interface?

isInterface() method The isArray() method of the Class class is used to check whether a class is an interface or not. This method returns true if the given class is an interface. Otherwise, the method returns false , indicating that the given class is not an interface.

Can a class implement multiple interfaces PHP?

A class can implement two interfaces which define a method with the same name, only if the method declaration in both interfaces is identical. A class that implements an interface may use a different name for its parameters than the interface.

Can a class implement an interface?

Your class can implement more than one interface, so the implements keyword is followed by a comma-separated list of the interfaces implemented by the class. By convention, the implements clause follows the extends clause, if there is one.

What is the difference between extends and implements in PHP?

Extends : This is used to get attributes of a parent class into base class and may contain already defined methods that can be overridden in the child class. Implements : This is used to implement an interface (parent class with functions signatures only but not their definitions) by defining it in the child class.


2 Answers

You can use class_implements (requires PHP 5.1.0)

interface MyInterface { } class MyClass implements MyInterface { }  $interfaces = class_implements('MyClass'); if($interfaces && in_array('MyInterface', $interfaces)) {     // Class MyClass implements interface MyInterface } 

You can pass the class name as a string as function's argument. Also, you may use Reflection

$class = new ReflectionClass('MyClass'); if ( $class->implementsInterface('MyInterface') ) {     // Class MyClass implements interface MyInterface } 

Update : (You may try something like this)

interface Programmer {     public function writeCode(); }  interface Actor {     // ... }  class BjarneProgrammer implements Programmer {     public function writeCode()     {         echo 'Implemented writeCode method from Programmer Interface!';     } } 

Function that checks and returns instanse/false

function getStudentObject($cls) {     $class = new ReflectionClass($cls);     if ( $class->implementsInterface('Programmer') ) {         return new $cls;     }     return false; } 

Get an instance or false

$students = array("BjarneProgrammer", "CharlieActor"); $c = getStudentObject($students[0]); if($c) {     $c->writeCode(); } 
like image 110
The Alpha Avatar answered Sep 20 '22 22:09

The Alpha


If you're using a modern version of PHP (5.3.9+), then the easiest (and best) way would be to use is_a() with the third parameter true:

$a = "Stdclass";  var_dump(is_a($a, "stdclass", true)); var_dump(is_a($a, $a, true)); 

Both of those will return true.

like image 27
ircmaxell Avatar answered Sep 20 '22 22:09

ircmaxell