Composer 自动加载的 PHP 版本问题疑惑?

Composer在初始化的时候,分为两种初始化方式:php版本为5.6以下的和php版本5.6以上的:

$useStaticLoader = PHP_VERSION_ID >= 50600 && !defined('HHVM_VERSION');
if ($useStaticLoader) {
   require_once __DIR__ . '/autoload_static.php';
   call_user_func(\Composer\Autoload\ComposerStaticInit
   832ea71bfb9a4128da8660baedaac82e::getInitializer($loader));
} else {
    $map = require __DIR__ . '/autoload_namespaces.php';
    foreach ($map as $namespace => $path) {
       $loader->set($namespace, $path);
    }
    $map = require __DIR__ . '/autoload_psr4.php';
    foreach ($map as $namespace => $path) {
       $loader->setPsr4($namespace, $path);
    }
    $classMap = require __DIR__ . '/autoload_classmap.php';
    if ($classMap) {
        $loader->addClassMap($classMap);
    }
  }

getInitializer函数:

     public static function getInitializer(ClassLoader $loader)
  {
    return \Closure::bind(function () use ($loader) {
        $loader->prefixLengthsPsr4 = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$prefixLengthsPsr4;
        $loader->prefixDirsPsr4 = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$prefixDirsPsr4;
        $loader->prefixesPsr0 = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$prefixesPsr0;
        $loader->classMap = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$classMap;
    }, null, ClassLoader::class);

其中classMap:

public static $classMap = array (
    'App\\Console\\Kernel' => __DIR__ . '/../..' . '/app/Console/Kernel.php',
    'App\\Exceptions\\Handler' => __DIR__ . '/../..' . '/app/Exceptions/Handler.php',
    'App\\Http\\Controllers\\Auth\\ForgotPasswordController' => __DIR__ . '/../..' . '/app/Http/Controllers/Auth/ForgotPasswordController.php',
    'App\\Http\\Controllers\\Auth\\LoginController' => __DIR__ . '/../..' . '/app/Http/Controllers/Auth/LoginController.php',
    'App\\Http\\Controllers\\Auth\\RegisterController' => __DIR__ . '/../..' . '/app/Http/Controllers/Auth/RegisterController.php',
    ...)

请问各位大牛,这段代码为神马要限制php版本5.6呢?我各处都没有找到原因,看了php的版本区别也没用头绪,请大牛解惑

《L01 基础入门》
我们将带你从零开发一个项目并部署到线上,本课程教授 Web 开发中专业、实用的技能,如 Git 工作流、Laravel Mix 前端工作流等。
《L05 电商实战》
从零开发一个电商项目,功能包括电商后台、商品 & SKU 管理、购物车、订单管理、支付宝支付、微信支付、订单退款流程、优惠券等
讨论数量: 11
leo

教楼主一个办法,通过 git blame 命令可以看到每一行代码是什么时候提交的,提交的日志是什么

https://github.com/composer/composer/blame...

https://github.com/composer/composer/commi...

另外我看我这边的composer代码,这4个属性确实是静态变量,可能低于5.6版本自动生成的类是私有属性。

6年前 评论

prefixLengthsPsr4,prefixDirsPsr4,prefixesPsr0classMap这四个属性都是静态属性,在PHP5.6之前不能使用如下的方式使用

$loader->prefixLengthsPsr4 = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$prefixLengthsPsr4;
$loader->prefixDirsPsr4 = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$prefixDirsPsr4;
$loader->prefixesPsr0 = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$prefixesPsr0;
$loader->classMap = ComposerStaticInit832ea71bfb9a4128da8660baedaac82e::$classMap;

可参考官方文档 https://secure.php.net/manual/en/language....

6年前 评论

@CraryPrimitiveMan 这个功能不是在php5.3就可以用了吗?这里限制的好严格啊

6年前 评论

@leoyang 上面不太对,但链接是对的。Like any other PHP static variable, static properties may only be initialized using a literal or constant before PHP 5.6

6年前 评论

@CraryPrimitiveMan soga,谢谢,大牛好厉害

6年前 评论

@CraryPrimitiveMan 突然发现个问题,prefixLengthsPsr4,prefixDirsPsr4,prefixesPsr0classMap并不是静态属性,他们只是private类型的

6年前 评论

@leo 我看ClassLoader类里面这四个属性刚刚有的时候就是private类型的,并没有static类型的时候,还有composer/src/Composer/Autoload/ClassLoader.php,这个文件是自动生成的吗?

6年前 评论

@leo 这四个成员在autoload_static文件ComposerStaticInit832ea71bfb9a4128da8660baedaac82e类中是静态的成员,我猜想是不是生成autoload_static.php的时候,利用的变量给这四个静态成员赋值。所以要求5.6以上是生成autoload_static文件的要求,如果版本低于5.6,autoload_static并不会存在?

6年前 评论

@leo 还有一种可能,static成员变量在 OPcache 中会被优化,这种优化机制只支持5.6以上的版本。也就是说只有5.6版本以上,这种static初始化才会更快,否则还是不用static的好

6年前 评论

大佬大佬@leoyang 看你的文章也想到了你这个问题,看了上面的回答感觉还是没解决,您现在有什么新的理解或者发现吗?

5年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!