laravel依赖注入原理

下例为官方文档,来认识一下反射



function bar(Exception $a, &$b, $c) { } $reflect = new ReflectionFunction('bar'); #$reflect object(ReflectionFunction)#1 (1) { ["name"]=> string(3) "bar" } foreach ($reflect->getParameters() as $i => $param) { #循环的第一次输出param object(ReflectionParameter)#2 (1) { ["name"]=> string(1) "a" } printf( "-- Parameter #%d: %s {\n". " Class: %s\n". " Allows NULL: %s\n". " Passed to by reference: %s\n". " Is optional?: %s\n". "}\n", $i, $param->getName(),#得到参数名 a var_export($param->getClass(), 1), #$param->getClass()输出为ReflectionClass::__set_state(array( 'name' => 'Exception', )) var_export($param->allowsNull(), 1), #参数是否可以为空,可以为空返回true; var_export($param->isPassedByReference(), 1),#如果参数是按引用传递,返回true; $param->isOptional() ? 'yes' : 'no' ); exit; } ?>

下例为laravel的依赖注入原理,代码来自https://phphub.org/topics/843;

<?php namespace Database; use ReflectionMethod; class Database { protected $adapter; public function __construct () {} public function test (MysqlAdapter $adapter) { $adapter->test(); } } class MysqlAdapter { public function test () { echo "i am MysqlAdapter test"; } } class app { public static function run ($instance, $method) { if (! method_exists($instance, $method)) return null; $reflector = new ReflectionMethod($instance, $method); #$reflector object(ReflectionMethod)#2 (2) { ["name"]=> string(4) "test" ["class"]=> string(17) "Database\Database" } $parameters = [ 1 ]; foreach ($reflector->getParameters() as $key => $parameter) #此处获得$method方法的需要的参数 #$parameter object(ReflectionParameter)#3 (1) { ["name"]=> string(7) "adapter" } { $class = $parameter->getClass(); if ($class) { array_splice($parameters, $key, 0, [ new $class->name() ]);#根据$method需要的参数,通过$class->name获得此参数的类型,然后生成一个此类型的对象,$parameters的开头处插入MysqlAdapter类型的对象 即$parameters=[MysqlAdapter对象,1] } } call_user_func_array([ $instance, $method ], $parameters);#调用$instance对象下的$method方法,将$parameters作为参数传递 } } app::run(new Database(), 'test');

总结:使用反射的意义在于,当传入一个对象和此对象包含的方法时;laravel通过反射来获取到此方法的参数列表,同时获取到参数的具体类型,然后根据此类型,生成对应的对象,供方法使用。

你可能感兴趣的:(reflect,laravel)