Core points
class_exists()
, get_class()
, get_parent_class()
, and is_subclass_of()
. These functions provide basic information about classes, such as their names, the names of the parent classes, and so on. ReflectionClass
Classes are the main classes of APIs that are used to apply reflections to classes, interfaces, and methods. PHP introspection is a common feature in any programming language that allows programmers to manipulate object classes. You will find introspection particularly useful when you don't know which class or method you need to execute when designing. Introspection in PHP provides useful functionality for checking classes, interfaces, properties, and methods. PHP provides a large number of functions that can be used to accomplish this task. To help you understand introspection, I will use the examples in PHP to briefly outline some of the classes, methods, and functions of PHP to highlight how they are used. In this article, you will see some examples on how to use some of the most useful PHP introspection functions, as well as a section dedicated to providing an API (Reflective API) similar to introspection.
PHP introspection function
In the first example, I will demonstrate some introspection functions of PHP. You can use these functions to extract basic information about classes, such as their names, the names of the parent class, and so on.
class_exists()
– Check if the class has been definedget_class()
– Return the object's class name get_parent_class()
– Returns the class name of the parent class of the object is_subclass_of()
– Check if the object has a given parent class The following is an example PHP code containing the Introspection
and Child
class definitions, as well as the information output extracted by the function listed above:
<?php class Introspection { public function description() { echo "I am a super class for the Child class.\n"; } } class Child extends Introspection { public function description() { echo "I'm " . get_class($this) , " class.\n"; echo "I'm " . get_parent_class($this) , "'s child.\n"; } } if (class_exists("Introspection")) { $introspection = new Introspection(); echo "The class name is: " . get_class($introspection) . "\n"; $introspection->description(); } if (class_exists("Child")) { $child = new Child(); $child->description(); if (is_subclass_of($child, "Introspection")) { echo "Yes, " . get_class($child) . " is a subclass of Introspection.\n"; } else { echo "No, " . get_class($child) . " is not a subclass of Introspection.\n"; } } ?>
The output of the above code should be as follows:
<?php class Introspection { public function description() { echo "I am a super class for the Child class.\n"; } } class Child extends Introspection { public function description() { echo "I'm " . get_class($this) , " class.\n"; echo "I'm " . get_parent_class($this) , "'s child.\n"; } } if (class_exists("Introspection")) { $introspection = new Introspection(); echo "The class name is: " . get_class($introspection) . "\n"; $introspection->description(); } if (class_exists("Child")) { $child = new Child(); $child->description(); if (is_subclass_of($child, "Introspection")) { echo "Yes, " . get_class($child) . " is a subclass of Introspection.\n"; } else { echo "No, " . get_class($child) . " is not a subclass of Introspection.\n"; } } ?>
You can use the class_exists()
method to determine whether the given class has been defined, which takes a string parameter that represents the name of the required class to be checked, and an optional boolean value indicating whether the autoloader is called during the procedure. The get_class()
and get_parent_class()
methods return the class name of the object or the class name of its parent class, respectively. Both take object instances as parameters. The is_subclass_of()
method takes the object instance as its first parameter and takes a string representing the parent class name as the second parameter, and returns whether the object belongs to a subclass of the class given as the parameter.
The following is a second example containing the definitions of the ICurrencyConverter
interface and the GBPCurrencyConverter
class, as well as the information output extracted by the functions listed above. As with the first example, I will first list the functions and then show you some code.
get_declared_classes()
– Return to a list of all declared classes get_class_methods()
– Return the name of the class method get_class_vars()
– Return the default attribute of the class interface_exists()
– Check if the interface is definedmethod_exists()
– Check whether the object defines a method<code>The class name is: Introspection I am a super class for the Child class. I'm Child class. I'm Introspection's child. Yes, Child is a subclass of Introspection.</code>
The output of the above code should be as follows:
<?php interface ICurrencyConverter { public function convert($currency, $amount); } class GBPCurrencyConverter implements ICurrencyConverter { public $name = "GBPCurrencyConverter"; public $rates = array("USD" => 0.622846, "AUD" => 0.643478); protected $var1; private $var2; function __construct() {} function convert($currency, $amount) { return $this->rates[$currency] * $amount; } } if (interface_exists("ICurrencyConverter")) { echo "ICurrencyConverter interface exists.\n"; } $classes = get_declared_classes(); echo "The following classes are available:\n"; print_r($classes); if (in_array("GBPCurrencyConverter", $classes)) { print "GBPCurrencyConverter is declared.\n"; $gbpConverter = new GBPCurrencyConverter(); $methods = get_class_methods($gbpConverter); echo "The following methods are available:\n"; print_r($methods); $vars = get_class_vars("GBPCurrencyConverter"); echo "The following properties are available:\n"; print_r($vars); echo "The method convert() exists for GBPCurrencyConverter: "; var_dump(method_exists($gbpConverter, "convert")); } ?>
As you may have guessed, the interface_exists()
method is very similar to the class_exists()
method discussed in the first example. It determines whether the given interface has been defined and takes a string parameter of the interface name and an optional autoloader boolean. The get_declared_classes()
method returns an array containing the names of all defined classes without any arguments. Depending on the library you loaded (compile into PHP or loaded using require
/include
), other classes may exist. get_class_method()
Takes an object instance or a string representing the required class as a parameter and returns an array of method names defined by the class. Note that of all properties defined in the ICurrencyConverter
class and all properties returned by the get_class_vars()
method, only $name
and $rates
appear in the output. Private and protected properties are skipped.
PHP Reflection API
PHP supports reflection through its reflection API. As you can see from the PHP manual, the reflection API is much more generous than the introspection mechanism and provides a large number of classes and methods that you can use to complete reflection tasks. ReflectionClass
Classes are the main class of the API, used to apply reflections to classes, interfaces, and methods, and extract information about all class components. Reflection is easy to implement in your application code and is as intuitive as introspection. Here is an example that illustrates reflection using the ICurrencyConverter
interface and Child
and GBPCurrencyConverter
classes:
<?php class Introspection { public function description() { echo "I am a super class for the Child class.\n"; } } class Child extends Introspection { public function description() { echo "I'm " . get_class($this) , " class.\n"; echo "I'm " . get_parent_class($this) , "'s child.\n"; } } if (class_exists("Introspection")) { $introspection = new Introspection(); echo "The class name is: " . get_class($introspection) . "\n"; $introspection->description(); } if (class_exists("Child")) { $child = new Child(); $child->description(); if (is_subclass_of($child, "Introspection")) { echo "Yes, " . get_class($child) . " is a subclass of Introspection.\n"; } else { echo "No, " . get_class($child) . " is not a subclass of Introspection.\n"; } } ?>
The output of the above code should be as follows:
<code>The class name is: Introspection I am a super class for the Child class. I'm Child class. I'm Introspection's child. Yes, Child is a subclass of Introspection.</code>
getInterfaceNames()
method returns an array containing the interface names of the class implementation. The getParentClass()
method can return the ReflectionClass
object representation of the parent class, and false if the parent class does not exist. To list the names of the ReflectionClass
objects, you can use the getName()
method, as shown in the above code. The getMethods()
method retrieves the method array and can combine bitmasks for ReflectionMethod::IS_STATIC
, IS_PUBLIC
, IS_PROTECTED
, IS_PRIVATE
, IS_ABSTRACT
, IS_FINAL
,
as optional parameters to filter the list based on visibility. The Reflection API provides a good implementation of reflection, allowing you to create more complex applications such as ApiGen, but further discussion goes beyond the goal of this article.
SummaryIn this article, you have learned how to use PHP's introspective functions and reflection APIs to get information about classes, interfaces, properties, and methods. The purpose of extracting this information is to better understand your code at runtime and create complex applications.
(Picture from Fotolia)(FAQ on Introspection and Reflection in PHP) The FAQ section is omitted here because it is too long and does not match the pseudo-original goal. If necessary, you can ask a FAQ question separately.
The above is the detailed content of Introspection and Reflection in PHP. For more information, please follow other related articles on the PHP Chinese website!