php自动加载机制的深入分析


Posted in PHP onJune 08, 2013

一、php中实现自动加载的方法
1.使用require,include,require_once,include_once手工进行加载。
2.使用__autoload来进行自动加载
3.使用spl的autoload来实现自动加载
手工加载的实现:

当需要加载的文件很少的时候我们可以使用第一个来完成。这样做很简单也没问题。

require_once 'a.php';
require_once 'b.php';
require_once 'c.php';

但是当需要加载文件很多的时候这样做还行吗?需要写十个,二十个require_once 或者更多的时候我们该怎么办?

这个时候我们可以使用__autoload方法来简化我们的代码。

__autoload加载的实现:
我们在test目录下创建一个in.php文件,内容如下。

echo '我是test下面的in.php<br />';

然后在test目录下创建一个loader.php,内容如下。
// 需要重载__autoload方法,自定义包含类文件的路径  
function __autoload($classname)  
{  
 $class_file = strtolower($classname).".php";  
 if (file_exists($class_file)){  
  require_once($class_file);  
 }  
}
@$test = new in(); // 执行到这里会输出 <SPAN style="FONT-FAMILY: Arial, Helvetica, sans-serif">我是test下面的in.php</SPAN>

没问题,成功了!我们还可以创建其他的文件来进行加载,但是当需要的文件很多需要区分目录的时候怎么办?

这时我们需要修改loader.php可以使用映射来找到要加载的文件。

function __autoload($class_name) {
 $map = array(
  'index' => './include/index.php',
  'in' => './in.php'
 );
    if (file_exists($map[$class_name]) && isset($map[$class_name])) {
        require_once $map[$class_name];
    }
}
new index();

这种方法的好处就是类名和文件路径只是用一个映射来维护,所以当文件结构改变的时候,不需要修改类名,只需要将映射中对应的项修改就好了。

但是__autoload在一个项目中只能使用一次,当你的项目引用了别人的一个项目,你的项目中有一个__autoload,别人的项目也有一个__autoload,这样两个__autoload就冲突了.解决的办法就是修改__autoload成为一个,这无疑是非常繁琐的,应用场景单一。

spl的autoload加载实现:
spl的autoload系列函数使用一个autoload调用堆栈,你可以使用spl_autoload_register注册多个自定义的autoload函数,应用场景广泛

php自动加载机制的深入分析

•在test目录下建立in.php,内容如下  

<?php
class in {
 public function index() {
  echo '我是test下面的in.php';
 }
}
?>

在test目录下建立loader.php,内容如下
<?php
set_include_path("/var/www/test/"); //这里需要将路径放入include
spl_autoload("in"); //寻找/var/www/test/in.php
$in = new in();
$in->index();

•spl_autoload_register将函数注册到SPL __autoload函数栈中,修改loader.php
function AutoLoad($class){
    if($class == 'in'){
        require_once("/var/www/test/in.php");
    }
}
spl_autoload_register('AutoLoad');
$a = new in();
$a->index();

•spl_autoload_register注册多个自定义的autoload函数的应用
首先在test目录下建立mods文件夹并建立inmod.mod.php内容如下:
<?php
class inmod
{
 function __construct()
 {
  echo '我是mods下的in';
 }
}

然后在test目录下建立libs文件夹并建立inlib.lib.php内容如下:
<?php
class inlib
{
 function __construct()
 {
  echo '我是libs下的in';
 }
}

最后在test目录下建立loader.php内容如下
<?php
class Loader {
    /**
    * 自动加载类
    * @param $class 类名
    */
    public static function mods($class) {
        if($class){
   set_include_path( "/var/www/test/mods/" );
   spl_autoload_extensions( ".mod.php" );
   spl_autoload( strtolower($class) );
        }
    }
    public static function libs($class) {
  if($class){
   set_include_path( "/var/www/test/libs/" );
   spl_autoload_extensions( ".lib.php" );
   spl_autoload( strtolower($class) );
        }
    }
}
spl_autoload_register(array('Loader', 'mods'));
spl_autoload_register(array('Loader', 'libs'));
new inmod();//输出<SPAN style="FONT-FAMILY: 'Times New Roman'; FONT-SIZE: 14px">我是mods下的in</SPAN>
new inlib();//<SPAN style="FONT-FAMILY: Arial, Helvetica, sans-serif">输出</SPAN><SPAN style="FONT-FAMILY: 'Times New Roman'; FONT-SIZE: 14px">我是libs下的in</SPAN>

PHP 相关文章推荐
用PHP获取Google AJAX Search API 数据的代码
Mar 12 PHP
yii2使用ajax返回json的实现方法
May 14 PHP
php处理静态页面:页面设置缓存时间实例
Jun 22 PHP
PHP实现自动发送邮件功能代码(qq 邮箱)
Aug 18 PHP
Laravel中encrypt和decrypt的实现方法
Sep 24 PHP
php表单处理操作
Nov 16 PHP
浅析PHP中的闭包和匿名函数
Dec 25 PHP
php intval函数用法总结
Apr 14 PHP
PHP实现字母数字混合验证码功能
Jul 11 PHP
PHP实现单条sql执行多个数据的insert语句方法
Oct 11 PHP
ThinkPHP 5.1 跨域配置方法
Oct 11 PHP
laravel框架使用极光推送消息操作示例
Feb 15 PHP
深入理解curl类,可用于模拟get,post和curl下载
Jun 08 #PHP
coreseek 搜索英文的问题详解
Jun 08 #PHP
探讨如何在php168_cms中提取验证码
Jun 08 #PHP
如何使用php绘制在图片上的正余弦曲线
Jun 08 #PHP
基于php常用正则表达式的整理汇总
Jun 08 #PHP
PHP计数器的实现代码
Jun 08 #PHP
使用cookie实现统计访问者登陆次数
Jun 08 #PHP
You might like
利用static实现表格的颜色隔行显示的代码
2007/09/02 PHP
php网页标题中文乱码的有效解决方法
2014/03/05 PHP
thinkphp框架下实现登录、注册、找回密码功能
2016/04/06 PHP
Javascript 陷阱 window全局对象
2008/11/26 Javascript
js创建数据共享接口——简化框架之间相互传值
2011/10/23 Javascript
微信企业号开发之微信考勤百度地图定位
2015/09/11 Javascript
javascript bom是什么及bom和dom的区别
2015/11/26 Javascript
jQuery学习心得总结(必看篇)
2016/06/10 Javascript
Bootstrap编写一个兼容主流浏览器的受众门户式风格页面
2016/07/01 Javascript
Vue.js每天必学之计算属性computed与$watch
2016/09/05 Javascript
JavaScript字符串对象
2017/01/14 Javascript
vue中appear的用法
2017/08/17 Javascript
Vue二次封装axios为插件使用详解
2018/05/21 Javascript
详解easyui基于 layui.laydate日期扩展组件
2018/07/18 Javascript
vue.js图片转Base64上传图片并预览的实现方法
2018/08/02 Javascript
Vue项目中最新用到的一些实用小技巧
2018/11/06 Javascript
vue实现的微信机器人聊天功能案例【附源码下载】
2019/02/18 Javascript
jQuery创建折叠式菜单
2019/06/15 jQuery
转换layUI的数据表格中的日期格式方法
2019/09/19 Javascript
js中的面向对象之对象常见创建方法详解
2019/12/16 Javascript
JS通用方法触发点击事件代码实例
2020/02/17 Javascript
bootstrap-table后端分页功能完整实例
2020/06/01 Javascript
python实现调用其他python脚本的方法
2014/10/05 Python
Python while 循环使用的简单实例
2016/06/08 Python
Python操作Access数据库基本步骤分析
2016/09/19 Python
Python制作词云的方法
2018/01/03 Python
python用户评论标签匹配的解决方法
2018/05/31 Python
Python生成MD5值的两种方法实例分析
2019/04/26 Python
解决jupyter notebook 前面书写后面内容消失的问题
2020/04/13 Python
python查询MySQL将数据写入Excel
2020/10/29 Python
pytorch 计算Parameter和FLOP的操作
2021/03/04 Python
毕业生应聘幼儿园的自荐信
2013/11/20 职场文书
机关干部正风肃纪心得体会
2016/01/15 职场文书
MySQL利用UNION连接2个查询排序失效详解
2021/11/20 MySQL
一篇文章告诉你如何实现Vue前端分页和后端分页
2022/02/18 Vue.js
Win11怎么跳过联网验机 ?Win11跳过联网验机激活教程
2022/04/05 数码科技