php 实现 ioc
PHP 实现 IOC(控制反转)容器
IOC(Inversion of Control)是一种设计模式,通过将对象的创建和管理交给容器来实现解耦。在 PHP 中,可以通过依赖注入(DI)和容器类来实现 IOC。
实现一个简单的 IOC 容器
以下是一个基础的 IOC 容器实现,支持绑定和解析依赖:
<?php
class Container {
protected $bindings = [];
// 绑定接口或抽象类到具体实现
public function bind($abstract, $concrete = null, $shared = false) {
if (is_null($concrete)) {
$concrete = $abstract;
}
$this->bindings[$abstract] = compact('concrete', 'shared');
}
// 解析实例
public function make($abstract) {
if (!isset($this->bindings[$abstract])) {
return $this->build($abstract);
}
$concrete = $this->bindings[$abstract]['concrete'];
$shared = $this->bindings[$abstract]['shared'];
if ($shared && isset($this->instances[$abstract])) {
return $this->instances[$abstract];
}
$object = $this->build($concrete);
if ($shared) {
$this->instances[$abstract] = $object;
}
return $object;
}
// 构建实例
protected function build($concrete) {
$reflector = new ReflectionClass($concrete);
if (!$reflector->isInstantiable()) {
throw new Exception("Class {$concrete} is not instantiable");
}
$constructor = $reflector->getConstructor();
if (is_null($constructor)) {
return new $concrete();
}
$dependencies = $constructor->getParameters();
$instances = $this->resolveDependencies($dependencies);
return $reflector->newInstanceArgs($instances);
}
// 解析依赖
protected function resolveDependencies($parameters) {
$dependencies = [];
foreach ($parameters as $parameter) {
$dependency = $parameter->getClass();
if (is_null($dependency)) {
if ($parameter->isDefaultValueAvailable()) {
$dependencies[] = $parameter->getDefaultValue();
} else {
throw new Exception("Cannot resolve dependency {$parameter->name}");
}
} else {
$dependencies[] = $this->make($dependency->name);
}
}
return $dependencies;
}
}
使用示例
定义一个接口和实现类:

interface LoggerInterface {
public function log($message);
}
class FileLogger implements LoggerInterface {
public function log($message) {
echo "Log to file: {$message}\n";
}
}
class DatabaseLogger implements LoggerInterface {
public function log($message) {
echo "Log to database: {$message}\n";
}
}
绑定并解析依赖:
$container = new Container();
// 绑定接口到具体实现
$container->bind(LoggerInterface::class, FileLogger::class);
// 解析实例
$logger = $container->make(LoggerInterface::class);
$logger->log("Hello IOC Container");
使用第三方库
对于更成熟的 IOC 容器实现,可以使用以下流行的 PHP 库:

- Laravel 的 IOC 容器:Laravel 框架内置了强大的 IOC 容器,可以直接使用或独立集成。
- PHP-DI:一个专为 PHP 设计的依赖注入容器,支持自动装配和注解。
- Pimple:一个轻量级的依赖注入容器,适合小型项目。
使用 PHP-DI 实现 IOC
安装 PHP-DI:
composer require php-di/php-di
示例代码:
<?php
require 'vendor/autoload.php';
use DI\Container;
use DI\ContainerBuilder;
$builder = new ContainerBuilder();
$builder->addDefinitions([
LoggerInterface::class => DI\create(FileLogger::class)
]);
$container = $builder->build();
$logger = $container->get(LoggerInterface::class);
$logger->log("Hello PHP-DI");
总结
实现 IOC 容器的核心是通过反射解析依赖并自动注入。自定义容器适合学习原理,而生产环境推荐使用成熟的库如 PHP-DI 或 Laravel 容器。






