使用子命名空间自动加载我的类 (Composer.json)

Posted

技术标签:

【中文标题】使用子命名空间自动加载我的类 (Composer.json)【英文标题】:Autoload My Classes with Sub-Namespaces (Composer.json) 【发布时间】:2016-07-01 10:15:37 【问题描述】:

我已将以下内容添加到我的 composer.json 文件中。这很好用,但我有一长串想要包含的子命名空间(例如 Apple、Orange、Lemon、Pear、Banana... 等)。

1) 我必须指出每个子命名空间还是有快捷方式,例如。 "Pure\\*": "pure"

composer.json:

"autoload": 

    "psr-4": 
        "Pure\\": "pure",
        "Pure\\Apple\\": "pure/src/Pure/Apple",
        "Pure\\Orange\\": "pure/src/Pure/Orange",
        "Pure\\Lemon\\": "pure/src/Pure/Lemon"

    

2) 包含自定义自动加载文件是否更好:

composer.json:

"autoload": 

    "files": [
      "pure/src/Pure/autoload.php"
    ]

autoload.php:

spl_autoload_register(function ($class) 

    //etc...

【问题讨论】:

您的第一行包含所有子命名空间。 如果我只包含第一行,我会得到Class 'Pure\Apple\Apple' not found 然后您需要拥有相对于纯文件夹的所有文件。即 Pure\Apple\Apple 必须在 pure/Apple/Apple.php 中 好的,完美。我的文件夹不正确。改为"Pure\\": "pure/src/Pure" 如果这是两个问题,最好将它们分开。 【参考方案1】:

我必须指出每个子命名空间还是有快捷方式

在声明自动加载时,应使用尽可能长或合理的前缀。

如果这个示例包是您创建的唯一一个,并且它是唯一一个使用Pure 作为命名空间的包,如果多个子目录中较长前缀的数量过多,请使用该示例包。但是,这假定您正在使用的世界上任何其他包都应该避免使用相同的命名空间做同样的事情。

Composer 将能够在所有可用目录中搜索子命名空间,即,如果您有两个包,一个说 Pure is to be found in pure/src/Pure,另一个说 Pure is in @987654326 @,Composer 将首先尝试在其中一个目录中找到一个类Pure\Something\Class,然后如果找不到则必须尝试第二个。 Composer 将记住 pure/src/Pure/Something 目录是否存在,如果必须加载该命名空间中的第二个类,则避免在该目录中查找以 Pure\Something 开头的任何内容。

但是从代码组织的角度来看,一个包应该只提供一组定义的命名空间,而其他任何包都不应该在同一命名空间中提供类。您可能会不小心将同一个类添加到两个包中,如果两个文件不同,可能会遇到一些难以调试的有趣问题。

包含自定义自动加载文件是否更好:

不,不惜一切代价避免它。您不会从中获得任何好处,因为文件总是必须被加载,并且它是占用一些内存的重复代码 - 您已经拥有 Composer 的自动加载器。如果您有不符合 PSR-4 或 PSR-0 的代码,则可以使用类映射。对于新代码:仅使用 PSR-4!

此外,Composer 无法优化您的自定义自动加载器。尽管应该衡量任何优化的有效性(请阅读我对此的详细回答:Why use a PSR-0 or PSR-4 autoload in composer if classmap is actually faster?),但如果有益的话,使用您自己的自动加载器将完全阻止您的代码被优化。

【讨论】:

以上是关于使用子命名空间自动加载我的类 (Composer.json)的主要内容,如果未能解决你的问题,请参考以下文章

将在自动加载的命名空间类文件中声明的函数转换为全局函数

Composer 自动加载几个路径作为一个命名空间

thinkphp 5.0 命名空间

Composer 自动加载始终是第一位的

thinkphp5.0命名空间

使用单个文件中的类作曲家自动加载