PHP中的use关键字及文件的加载详解


Posted in PHP onNovember 28, 2016

前言

可能在大家经常使用框架,写一个Controller或者Model的时候,写了好多use,但是并没有写文件加载的代码,就以为use可以进行文件的自动加载了。

详细介绍

其实,现在流行的php框架,都是基于MVC模式的,大量的使用了命名空间,以提高程序的灵活性。那么框架是怎么实现将use关键字所声明的类库对应的脚本文件进行加载的那?

(1):在通过use关键字进行声明类库的声明的时候,并不会进行脚本的加载,而是在脚本文件真正使用到所对应的类库的时候才会进行加载(这就是所谓延迟加载)。

(2):框架一般在初始化阶段,就声明了__autoload()函数或者是spl_autoload_register()函数(一般会在入口文件中进行声明)。在调用通过use声明的类库的时候,会自动的调用上述的函数,将调用的类库名称传递到函数中(这里的类库名称是包括命名空间的全名称)

<?php
namespace Home\Controller;
function __autoload($class_name) { 
 //echo $class_name."<br/>"; 
 require_once ("./".$class_name . ".php");  
}
use Admin\Controller\Index;
new Index; //new Index会触发__autoload()函数,返回Admin\Controller\Index到函数中
?>

(3):框架中定义的__autoload()函数或者是spl_autoload_register()函数在接收到传递过来的类库名称以后,框架会对名称进行处理,分析出类库名称所对应的文件路径,然后进行文件的加载。这里需要注意的是,不同的框架在解析类库名称,分析文件路径的方式是各不一致的,毕竟各自的目录结构是不一样的。

比如说,thinkphp:

/**
  * 类库自动加载
  * @param string $class 对象类名
  * @return void
  */
 public static function autoload($class) {
  // 检查是否存在映射
  if(isset(self::$_map[$class])) {
   include self::$_map[$class];
  }elseif(false !== strpos($class,'\\')){
   $name   = strstr($class, '\\', true);
   if(in_array($name,array('Think','Org','Behavior','Com','Vendor')) || is_dir(LIB_PATH.$name)){ 
    // Library目录下面的命名空间自动定位
    $path  = LIB_PATH;
   }else{
    // 检测自定义命名空间 否则就以模块为命名空间
    $namespace = C('AUTOLOAD_NAMESPACE');
    $path  = isset($namespace[$name])? dirname($namespace[$name]).'/' : APP_PATH;
   }
   $filename  = $path . str_replace('\\', '/', $class) . EXT;
   if(is_file($filename)) {
    // Win环境下面严格区分大小写
    if (IS_WIN && false === strpos(str_replace('/', '\\', realpath($filename)), $class . EXT)){
     return ;
    }
    include $filename;
   }
  }elseif (!C('APP_USE_NAMESPACE')) {
   // 自动加载的类库层
   foreach(explode(',',C('APP_AUTOLOAD_LAYER')) as $layer){
    if(substr($class,-strlen($layer))==$layer){
     if(require_cache(MODULE_PATH.$layer.'/'.$class.EXT)) {
      return ;
     }
    }   
   }
   // 根据自动加载路径设置进行尝试搜索
   foreach (explode(',',C('APP_AUTOLOAD_PATH')) as $path){
    if(import($path.'.'.$class))
     // 如果加载类成功则返回
     return ;
   }
  }
 }

这里只是举例说明use与文件的自动加载没有关系,不强调各个框架是具体怎么完成自动加载,具体的可以自己看框架代码进行研究。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流。

PHP 相关文章推荐
社区(php&amp;&amp;mysql)四
Oct 09 PHP
使用PHP数组实现无限分类,不使用数据库,不使用递归.
Dec 09 PHP
php在线生成ico文件的代码
Oct 09 PHP
解析php中array_merge与array+array的区别
Jun 21 PHP
php生成excel文件的简单方法
Feb 08 PHP
PHP语法自动检查的Vim插件
Aug 11 PHP
PHP Streams(流)详细介绍及使用
May 12 PHP
PHP开发的微信现金红包功能示例
Jun 29 PHP
php利用云片网实现短信验证码功能的示例代码
Nov 18 PHP
Laravel 加载第三方类库的方法
Apr 20 PHP
PHP PDOStatement::fetchColumn讲解
Jan 31 PHP
PHP编程一定要改掉的5个不良习惯
Sep 18 PHP
php连接微软MSSQL(sql server)完全攻略
Nov 27 #PHP
php源码之将图片转化为data/base64数据流实例详解
Nov 27 #PHP
PHP使用curl函数发送Post请求的注意事项
Nov 26 #PHP
laravel创建类似ThinPHP中functions.php的全局函数
Nov 26 #PHP
PHP数组相加操作及与array_merge的区别浅析
Nov 26 #PHP
PHP中call_user_func_array回调函数的用法示例
Nov 26 #PHP
PHP 匿名函数与注意事项详细介绍
Nov 26 #PHP
You might like
php GD绘制24小时柱状图
2008/06/28 PHP
DISCUZ 论坛管理员密码忘记的解决方法
2009/05/14 PHP
destoon利用Rewrite规则设置网站安全
2014/06/21 PHP
php创建图像具体步骤
2017/03/13 PHP
基于win2003虚拟机中apache服务器的访问
2017/08/01 PHP
js innerHTML 改变div内容的方法
2013/08/03 Javascript
当json键为数字时的取值方法解析
2013/11/15 Javascript
jquery默认校验规则整理
2014/03/24 Javascript
浏览器窗口大小变化时使用resize事件对框架不起作用的解决方法
2014/05/11 Javascript
javascript实现控制的多级下拉菜单
2015/07/05 Javascript
jQuery实现鼠标经过时出现隐藏层文字链接的方法
2015/10/12 Javascript
Bootstrop实现多级下拉菜单功能
2016/11/24 Javascript
完美解决axios在ie下的兼容性问题
2018/03/05 Javascript
利用原生JS实现欢乐水果机小游戏
2020/04/23 Javascript
vue-cli3项目配置eslint代码规范的完整步骤
2020/09/10 Javascript
Vue 防止短时间内连续点击后多次触发请求的操作
2020/11/11 Javascript
[03:20]次级联赛厮杀超职业 现超级兵对拆世纪大战
2014/10/30 DOTA
[00:47]DOTA2荣耀之路6:天火,天火!
2018/05/30 DOTA
[54:09]RNG vs Liquid 2019国际邀请赛淘汰赛 败者组 BO3 第一场 8.23
2019/09/05 DOTA
python从入门到精通(DAY 2)
2015/12/20 Python
Python3 中文文件读写方法
2018/01/23 Python
Python运行不显示DOS窗口的解决方法
2018/10/22 Python
python获取时间及时间格式转换问题实例代码详解
2018/12/06 Python
Python3获取电脑IP、主机名、Mac地址的方法示例
2019/04/11 Python
Django框架登录加上验证码校验实现验证功能示例
2019/05/23 Python
在Mac中配置Python虚拟环境过程解析
2020/06/22 Python
使用python tkinter开发一个爬取B站直播弹幕工具的实现代码
2021/02/07 Python
使用HTML5 Geolocation实现一个距离追踪器
2018/04/09 HTML / CSS
美国保健品专家:Life Extension
2018/05/04 全球购物
be2台湾单身男女交友:全球网路婚姻介绍的领导品牌
2019/10/11 全球购物
高级技校毕业生自荐信
2013/11/18 职场文书
教师师德师风自我剖析材料
2014/09/29 职场文书
灵山大佛导游词
2015/02/04 职场文书
2015年电话客服工作总结
2015/05/18 职场文书
实践论读书笔记
2015/06/29 职场文书
行政复议答复书
2015/07/01 职场文书