PHP implementation of the reflection mechanism automatic dependency Injection detailed

Source: Internet
Author: User
This article describes how PHP implements the reflection mechanism and automatically relies on injected, not much understanding of the PHP reflection mechanism and automatic dependency injection of the students, let's take a look at this article!

Dependency injection is also called control reversal, and people who have used frames should not be strangers. A lot of people look at the name of a very tall thing, on it deterred, today time to study the next, untie his mysterious veil. Nonsense not much to say, directly on the code;

The/**** tool class that uses this class to implement automatic dependency injection. **/class Ioc {//Get object instance of class public static function getinstance ($className) {$PARAMARR = Self::getmethodparams        ($className);    Return (new Reflectionclass ($className))->newinstanceargs ($PARAMARR); }/** * Method of executing class * @param [Type] $className [class name] * @param [Type] $methodName [method name] * @param [type] $ params [Additional parameters] * @return [type] [description] */public static function make ($className, $metho        Dname, $params = []) {//Gets an instance of the class $instance = Self::getinstance ($className);        Gets the parameter $PARAMARR = Self::getmethodparams ($className, $methodName) for which the method requires dependency injection;    return $instance->{$methodName} (Array_merge ($PARAMARR, $params)); }/** * Gets the method parameter of the class, obtains only the type parameter * @param [type] $className [description] * @param [type] $methodsName [descr Iption] * @return [type] [description] */protected static function Getmethodparams ($className, $m EthoDSName = ' construct ') {//through reflection to obtain the class $class = new Reflectionclass ($className); $PARAMARR = []; Record parameters, and parameter types//determine if the class has a constructor if ($class->hasmethod ($methodsName)) {//Get the constructor $cons            Truct = $class->getmethod ($methodsName);            Determine if the constructor has parameters $params = $construct->getparameters ();                    if (count ($params) > 0) {//Determine parameter type foreach ($params as $key + = $param) { if ($paramClass = $param->getclass ()) {//Gets the parameter type name $paramClassNam                        E = $paramClass->getname ();                        Get the parameter type $args = Self::getmethodparams ($paramClassName);                    $PARAMARR [] = (new Reflectionclass ($paramClass->getname ()))->newinstanceargs ($args);    }}}} return $PARAMARR; }}

The above code uses the PHP reflection function to create a container class that uses this class to implement the dependency injection capabilities of other classes. The above dependency injection is divided into two types, one is the dependency injection of the constructor, and the other is the method's dependency injection. We use the following three classes to do the next test.

Class A {    protected $cObj;    /**     * For testing multistage Dependency Injection B dependent a,a dependent c     * @param c $c [description]     *    /Public Function construct (C $c) {        $this-& Gt;cobj = $c;    }    Public Function aa () {        echo ' this is A->test ';    }    Public Function AAC () {        $this->cobj->cc ();    }} Class B {    protected $aObj;    /**     * Test Constructor Dependency Injection     * @param a $a [use attract inject a]     */public    function construct (a $a) {        $this->aobj = $ A;    }    /**     * [test method call Dependency Injection]     * @param  C      $c [Dependency Injection C]     * @param  string $b [This is the parameter that I manually fill]     * @ return [Type]    [description]     */public    function bb (C $c, $b) {        $c->cc ();        echo "\ r \ n";        echo ' params: '. $b;    }    /**     * Verify that the dependency injection succeeded     * @return [Type] [description] *     /public    function bbb () {        $this->aobj- >AAC ();    }} Class C {public    function cc () {        echo ' this is c->cc ';    }}

1. Test the dependency injection of the constructor function

Using IOC to create an instance of Class B, the constructor of B relies on Class A, and A's constructor relies on Class C. $BOBJ = ioc::getinstance (' B '); $bObj->bbb (); Output: This is C->CC, indicating a successful dependency injection. Print $bobjvar_dump ($BOBJ);//printing results, you can see that B has an instance of a, a C instance, indicating the success of dependency injection. Object (B) #3 (1) {  ["aobj":p rotected]=>  Object (A) #7 (1) {    ["CObj":p rotected]=>    Object (C) #10 (0 ) {    }  }}

2. Test method Dependency Injection

Ioc::make (' b ', ' BB ', [' This is Param B ']);//output, you can see the success of dependency injection. This is c->ccparams:this is param b

As you can see from the two examples above, when we create an object or invoke a method, we don't have to know that the class or the method depends on that class. Using the reflection mechanism makes it easy for us to automatically inject the required classes.

Summarize

OK, see the above code is not very simple, in fact, as long as the knowledge of the reflection mechanism of PHP, dependency injection is not difficult to achieve, the above code in order to facilitate understanding, so simple to write the violence, in the actual project will not be so simple, such as: will be injected with the class and parameters, such as the cache instantiated classes, The next time an instance of the class is needed, it can be used directly, instead of being reinitialized, and so on. However, I believe that the principle of understanding, the other can be the project with the needs of their own to improve.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.