Composer与自动加载

本文详细介绍了Composer自动加载机制,特别是PSR-4规范的运用。PSR-4规定了类名与文件路径的映射规则,用于自动载入类文件。Composer通过composer.json生成autoload文件,建立命名空间与文件路径的映射。在项目运行时,通过ClassLoader的loadClass方法按规则查找并引入所需类文件。自动加载提升了代码的组织效率,简化了依赖管理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Composer与自动加载

PSR-4

这个 PSR 描述的是通过文件路径 自动载入 类的指南;它作为对 PSR-0 的补充;根据这个 指导如何规范存放文件来自动载入;
术语「类」是一个泛称;它包含类,接口,traits 以及其他类似的结构;

完全限定类名应该类似如下范例:

()*

完全限定类名必须有一个顶级命名空间(Vendor Name);
完全限定类名可以有多个子命名空间;
完全限定类名应该有一个终止类名;
下划线在完全限定类名中是没有特殊含义的;
字母在完全限定类名中可以是任何大小写的组合;
所有类名必须以大小写敏感的方式引用;
当从完全限定类名载入文件时:

在完全限定类名中,连续的一个或几个子命名空间构成的命名空间前缀(不包括顶级命名空间的分隔符),至少对应着至少一个基础目录。
在「命名空间前缀」后的连续子命名空间名称对应一个「基础目录」下的子目录,其中的命名 空间分隔符表示目录分隔符。子目录名称必须和子命名空间名大小写匹配;
终止类名对应一个以 .php 结尾的文件。文件名必须和终止类名大小写匹配;
自动载入器的实现不可抛出任何异常,不可引发任何等级的错误;也不应返回值;

自动加载是用到了 spl_autoload_register函数,spl_autoload_register(array(class,load));load自定义函数,class为定义load的类,load是自定义函数,函数中写了通过class寻找目标文件与引入。

Composer的自动加载

使用自动加载时,先通过名称空间的前缀,找到对应的映射路径,在根据PSR0规范找到对应的类定义文件。但是这里有些例外,类名中的下划线在PSR4中是不需要转换成目录的。

composer中的自动加载,通过composer.json生成autoload_psr4.php,autoload_psr0.phpautoload_classmap等文件,这些文件保存这命名空间与目标文件的映射目录

在引入vender/autoload.php,通过 ComposerAutoloaderInit获取load对象,

 public static function getLoader()
    {
        if (null !== self::$loader) {
            return self::$loader;
        }

        require __DIR__ . '/platform_check.php';

        spl_autoload_register(array('ComposerAutoloaderInit5b6df0852e175d157f350339232d00ce', 'loadClassLoader'), true, true);
        self::$loader = $loader = new \Composer\Autoload\ClassLoader();//获取loader对象
        spl_autoload_unregister(array('ComposerAutoloaderInit5b6df0852e175d157f350339232d00ce', 'loadClassLoader'));

        $useStaticLoader = PHP_VERSION_ID >= 50600 && !defined('HHVM_VERSION') && (!function_exists('zend_loader_file_encoded') || !zend_loader_file_encoded());
        if ($useStaticLoader) {
            require __DIR__ . '/autoload_static.php';

            call_user_func(\Composer\Autoload\ComposerStaticInit5b6df0852e175d157f350339232d00ce::getInitializer($loader));
        } else {
            $map = require __DIR__ . '/autoload_namespaces.php';
            foreach ($map as $namespace => $path) {
                $loader->set($namespace, $path);
            }

            $map = require __DIR__ . '/autoload_psr4.php';###此处加载psr4标准的文件
            foreach ($map as $namespace => $path) {
                $loader->setPsr4($namespace, $path);###将psr4的命名空间与目标路径的规则
            }

            $classMap = require __DIR__ . '/autoload_classmap.php';
            if ($classMap) {
                $loader->addClassMap($classMap);
            }
        }

        $loader->register(true);##通过loader与resiter完成注册

        return $loader;
    }
####   'Library\\sso\\' => array($baseDir . '/Library/sso'), psr4的命名空间与路径的映射关系
public function setPsr4($prefix, $paths)
    {
        if (!$prefix) {
            $this->fallbackDirsPsr4 = (array) $paths;
        } else {
            $length = strlen($prefix);
            if ('\\' !== $prefix[$length - 1]) {
                throw new \InvalidArgumentException("A non-empty PSR-4 prefix must end with a namespace separator.");
            }
            $this->prefixLengthsPsr4[$prefix[0]][$prefix] = $length;//###设置 loader命名空间的长度 这个是方便检索,快速查找命名空间是否注册在psr4中 
            $this->prefixDirsPsr4[$prefix] = (array) $paths; //规则设置到的 loader的psr4的注册表中
        }
    }

当在项目中遇到为引入的的类,则会触发classloader中的loadClass函数 ,函数通过classloader的注册数组寻找类的所在目录并引人文件。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值