首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >CodeIgniter (CI) 框架学习 -- load_class

CodeIgniter (CI) 框架学习 -- load_class

作者头像
lpe234
发布2020-07-27 17:15:06
1.2K0
发布2020-07-27 17:15:06
举报
文章被收录于专栏:若是烟花若是烟花

文档是前提,没有捷径。 http://codeigniter.org.cn/user_guide/index.html


一、源码

// ..system/core/Common.php

if ( ! function_exists('load_class'))
{
	/**
	 * Class registry
	 *
	 * This function acts as a singleton. If the requested class does not
	 * exist it is instantiated and set to a static variable. If it has
	 * previously been instantiated the variable is returned.
	 *
	 * @param	string	the class name being requested
	 * @param	string	the directory where the class should be found
	 * @param	string	an optional argument to pass to the class constructor
	 * @return	object
	 */
	function &load_class($class, $directory = 'libraries', $param = NULL)
	{
		static $_classes = array();

		// Does the class exist? If so, we're done...
		if (isset($_classes[$class]))
		{
			return $_classes[$class];
		}

		$name = FALSE;

		// Look for the class first in the local application/libraries folder
		// then in the native system/libraries folder
		foreach (array(APPPATH, BASEPATH) as $path)
		{
			if (file_exists($path.$directory.'/'.$class.'.php'))
			{
				$name = 'CI_'.$class;

				if (class_exists($name, FALSE) === FALSE)
				{
					require_once($path.$directory.'/'.$class.'.php');
				}

				break;
			}
		}

		// Is the request a class extension? If so we load it too
		if (file_exists(APPPATH.$directory.'/'.config_item('subclass_prefix').$class.'.php'))
		{
			$name = config_item('subclass_prefix').$class;

			if (class_exists($name, FALSE) === FALSE)
			{
				require_once(APPPATH.$directory.'/'.$name.'.php');
			}
		}

		// Did we find the class?
		if ($name === FALSE)
		{
			// Note: We use exit() rather than show_error() in order to avoid a
			// self-referencing loop with the Exceptions class
			set_status_header(503);
			echo 'Unable to locate the specified class: '.$class.'.php';
			exit(5); // EXIT_UNK_CLASS
		}

		// Keep track of what we just loaded
		is_loaded($class);

		$_classes[$class] = isset($param)
			? new $name($param)
			: new $name();
		return $_classes[$class];
	}
}

先找个调用的例子吧。

$CFG =& load_class('Config', 'core');

此处是“加载”了配置类。

二、源码分析

1. “&”符号

$CFG =& load_class('Config', 'core');

其中: 比较重要的是 “&”符号,定义函数和调用函数时,均有使用。在此处是获得返回对象的引用。

2. “function_exists”

一般加载公共函数时使用,判断当前环境是否存在该函数。以判断是否需要继续加载

3. 代码片段
// Look for the class first in the local application/libraries folder
// then in the native system/libraries folder
// APPPATH 为CI的application文件夹绝对地址(文件夹名称可修改,在index.php中。详细参见文档。)
// BASEPATH 为CI的system文件夹绝对地址
foreach (array(APPPATH, BASEPATH) as $path)
{
	if (file_exists($path.$directory.'/'.$class.'.php'))
	{
        // CI框架自己的类使用了"CI_"前缀
		$name = 'CI_'.$class;
        
        // 判断当前环境中是否存在该类,参数$autoload=FALSE 不自动加载
		if (class_exists($name, FALSE) === FALSE)
		{
            // 加载该文件
			require_once($path.$directory.'/'.$class.'.php');
		}

		break;
	}
}
// Is the request a class extension? If so we load it too
// 是否是请求加载一个类扩展?如果是 我们也同样加载它

// 判断在 ..application/xxx 文件夹下面是否存在这个文件
// subclass_prefix 配置见 下面的代码段
if (file_exists(APPPATH.$directory.'/'.config_item('subclass_prefix').$class.'.php'))
{
	$name = config_item('subclass_prefix').$class;

	if (class_exists($name, FALSE) === FALSE)
	{
		require_once(APPPATH.$directory.'/'.$name.'.php');
	}
}


//-------------------- ..config/config.php
/*
|--------------------------------------------------------------------------
| Class Extension Prefix
|--------------------------------------------------------------------------
|
| This item allows you to set the filename/classname prefix when extending
| native libraries.  For more information please see the user guide:
|
| https://codeigniter.com/user_guide/general/core_classes.html
| https://codeigniter.com/user_guide/general/creating_libraries.html
|
*/
// 当你扩展本地库时,这一项允许你设置前缀。 比如: class MY_Config
$config['subclass_prefix'] = 'MY_';
// 这块为加载完类之后, 返回一个对象。 
// 由于函数定义及引用时,使用了“&” 此处创建的对象,也就等同于调用该函数时得到的返回对象。
$_classes[$class] = isset($param)? new $name($param) : new $name();


//------------------------字符串变量创建对象

class XX {}

$class_name = 'XX';

$class = new $class_name(); // 即可创建对象

三、精简示例

// 假设存在这么一个 "XX.php"文件,里面包含一个 "X_XX"类
function &load_xx() {
    require_once 'XX.php';
    $name = 'X__XX';
    $entry = new $name();
    return $entry;
}

// $x 即为函数创建的类对象引用
$x =& load_xx();
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、源码
  • 二、源码分析
    • 1. “&”符号
      • 2. “function_exists”
        • 3. 代码片段
        • 三、精简示例
        领券
        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档