已经有了非常好的Pimple的相关解析,建议先看下:
Pimple - 一个简单的 PHP 依赖注入容器
读 PHP - Pimple 源码笔记(上)
读 PHP - Pimple 源码笔记(下)

这里通过例子补充下核心方法的说明:
相关的类型:

  1. 服务(类似单例):


    $container['session'] = function ($c) {
    return new Session($c['session_storage']);
    };
  2. 工厂服务(多个实例)


    $container['session'] = $container->factory(function ($c) {
    return new Session($c['session_storage']);
    });
  3. 参数(仅仅是保存一些变量)


    $container['cookie_name'] = 'SESSION_ID';
  4. 保护参数(匿名函数都会被认为【1服务】,但是如果仅仅是想作为一个参数,则需要用此方法)


    $container['random_func'] = $container->protect(function () {
    return rand();
    });

set赋值相关源码:


public function offsetSet($id, $value)
{
//如果是被冻结,则无法赋值
if (isset($this->frozen[$id])) {
throw new FrozenServiceException($id);
}
//存入values
$this->values[$id] = $value;
//存入keys
$this->keys[$id] = true;
}

用【1服务】来举例,调用offsetSet方法后:


$this->values['session'] = function ($c) {
return new Session($c['session_storage']);
};
$this->keys['session'] = true;

使用时$session=$container['session'];,此时调用offsetGet方法:


public function offsetGet($id)
{
//$this->keys['session']存在
if (!isset($this->keys[$id])) {
throw new UnknownIdentifierException($id);
} if (
isset($this->raw[$id])//$this->raw['session'],第一次调用是没有的,所以为false,重复调用则为ture
|| !\is_object($this->values[$id])//所有的匿名函数都是object,所以为false。对应的情况【3参数】时为true
|| isset($this->protected[$this->values[$id]])//未调用protected方法,所以为false,对应的情况【4保护参数】时为true
|| !\method_exists($this->values[$id], '__invoke')//所有匿名函数存在__invoke方法,所以为false
) {
//综上,如果是第一次调用,不会执行到这一步,如果是重复调用、参数、protected方法相关的,则会执行
return $this->values[$id];
}
//判定是不是多个实例,对应【2工厂服务】,由于我们没有调用factories方法,所以这一步也不会执行
if (isset($this->factories[$this->values[$id]])) {
return $this->values[$id]($this);
} //此时$raw就是function ($c) 这个匿名函数
$raw = $this->values[$id]; //重新赋值$this->values['session'],将$this传入,相当于function ($this),之所以把$this传递过来,是因为匿名函数中可能还包含其它的服务,
//例如上方的$c['session_storage'],$this传入后相当于$container['session_storage'],此时会触发调用offsetGet此方法。
$val = $this->values[$id] = $raw($this); //将原始的匿名函数存入$this->raw中,$this->raw['session']此时有值,重复访问时在上方判定时直接返回,相当于单例模式
$this->raw[$id] = $raw; //标记已冻结,已经get后则不允许offsetSet或者extend了
$this->frozen[$id] = true; //返回$this->values['session']
return $val;
}

Pimple实现起来比较简单,主要是通过匿名函数来实现,没有像yii2容器那样支持普通类的构造函数自动解析依赖注入关系等,但是对于仅仅是调用各个组件来说也足够用了。

原文地址:https://segmentfault.com/a/1190000016747497

Pimple相关的源码的更多相关文章

  1. List 接口以及实现类和相关类源码分析

    List 接口以及实现类和相关类源码分析 List接口分析 接口描述 用户可以对列表进行随机的读取(get),插入(add),删除(remove),修改(set),也可批量增加(addAll),删除( ...

  2. fork()相关的源码解析

    fork()的真正执行采用的是do_fork()函数,所以下文将从do_fork()函数对fork()进行源码解析.下图是do_fork()的源码函数设计: 从上图我们可以看到do_fork()涉及到 ...

  3. 分享一些阅读Java相关框架源码的经验

    昨天和部分网友进行了线上的交流,交流中有不少网友提到阅读源码比较难,不知道怎么上手.胖哥分享了一些个人经验,这里总结一下. 阅读源码实际上是Debug源码 其实所谓的阅读源码并不是单纯的阅读,而是调试 ...

  4. Cocos2d-X3.0 刨根问底(八)----- 场景(Scene)、层(Layer)相关源码分析

    本章节我们重点分析Cocos2d-x3.0与 场景.层相关的源码.这部分源码集中在 libcocos2d –> layers_scenes_transitions_nodes目录下面 我先发个截 ...

  5. Android AdapterView 源码分析以及其相关回收机制的分析

    忽然,发现,网上的公开资料都是教你怎么继承一个baseadapter,然后重写那几个方法,再调用相关view的 setAdpater()方法, 接着,你的item 就显示在手机屏幕上了.很少有人关注a ...

  6. motan源码分析五:cluster相关

    上一章我们分析了客户端调用服务端相关的源码,但是到了cluster里面的部分我们就没有分析了,本章将深入分析cluster和它的相关支持类. 1.clustersupport的创建过程,上一章的Ref ...

  7. react 中间件相关的一些源码解析

    零.随便说说中间件 在react的使用中,我们可以将数据放到redux,甚至将一些数据相关的业务逻辑放到redux,这样可以简化我们组件,也更方便组件抽离.封装.复用,只是redux不能很好的处理异步 ...

  8. Spring:源码解读Spring IOC原理

    Spring IOC设计原理解析:本文乃学习整理参考而来 一. 什么是Ioc/DI? 二. Spring IOC体系结构 (1) BeanFactory (2) BeanDefinition 三. I ...

  9. redis 源码阅读 内部数据结构--字符串

    redis的内部数据结构主要有:字符串,双端链表,字典,跳跃表. 这里主要记录redise字符串的设计.相关的源码位于:src/sds.h 和 src/sds.c.   一 字符串 sds的结构体 s ...

随机推荐

  1. web 安全主题

  2. UVA10082-WERTYU(紫书例题3.2)

    A common typing error is to place the hands on the keyboard one row to the right of the correct posi ...

  3. docker 镜像的导入导出

    今天使用docker部署asp.net core应用程序时,发现当我们做好基础镜像之后需要把镜像导出到正式环境,因此学习了一下如何从docker中导出镜像: 1.首先通过docker images命令 ...

  4. Linux赛车游戏 SuperTuxKart 1.0 正式发布

    SuperTuxKart是一款受Mario Kart(马里奥赛车)启发并以Linux/Tux为主题的开源赛车游戏,经过12年多的开发,已经达到1.0版本.并且确定这个版本确实是一个重要的里程碑. Su ...

  5. Android开发进度07

    1,今日:目标:完成记账功能 2,昨天:账单的增删改查方法 3,收获:无 4,问题:SQLite表单出现问题,提交后软件直接退出

  6. apche本地测试,无法访问此网站

  7. UVALive 3231 Fair Share

    Fair Share Time Limit: 3000ms Memory Limit: 131072KB This problem will be judged on UVALive. Origina ...

  8. java深克隆与浅克隆

    2015.9.19 6:45   星期五    1

  9. Spring+Mybatis+SpringMVC后台与前台分页展示实例

    摘要:本文实现了一个后台由spring+Mybatis+SpringMVC组成,分页采用PageHelper,前台展示使用bootstrap-paginator来显示效果的分页实例.整个项目由mave ...

  10. WinServer-IIS-IIS负载均衡

    安装应用程序路由 提供的服务器的地址必须是可以访问,不然无法进入到下面的这个管理界面 来自为知笔记(Wiz)