使用 switch-case 按类型创建不同的对象?

Create different object by type using switch-case?

大家好,

我们使用很多语句,例如 if-else 或 switch-case 来根据不同的条件创建不同的对象,例如:

interface Job {
    public function do();
}

class Auto implement Job {
    ...
}

class Month implement Job {
    ...
}

...
// another script to run jobs
...
switch($type) {
    case 'auto':
        $instance = new Auto();
        break;
    case 'month':
        $instance = new Month();
        break;
    default:
        throw new Exception('not support type!');
}

$instance->do();

问题是如果我们使用 if-else / switch-case 会使代码随着类型的增加而快速增长。
我们可以使用反射或动态实例启动,但是 IDE(如 PHPStorm)将无法找到 class 用法..
有没有更好的方法来避免使用 switch-case?

真的有两个答案。

您应该将类​​型提示 $instance 作为接口 Job。这就是 OOP 中 Interface 的全部目的。您可以通过以下方式做到这一点:

switch ($type) {
    case 'auto':
        $instance = new Auto();
        break;
    // ...
}

/** @var \Job $instance */
$instance->do();

如果您想走那条路,您可以为类型提示工厂方法向 PHPStorm 提供元数据。元数据文件可以像您的代码一样提交到源代码管理 https://confluence.jetbrains.com/display/PhpStorm/PhpStorm+Advanced+Metadata