将四个 classes 中的任何一个注入 class

Inject any of four classes into a class

我有一个 class(我们称之为 TestClassA),其中构造函数看起来像这样

public function __constructor(SomeInterface $some, AnotherInterface $another, $additionalArgs = null)
{
    // Rest of code
}

$additionalArgs 的值可以来自四个唯一的 class 中的任何一个。这些 class 中的每一个都会根据用户的条件集向上面的 class 添加唯一的查询参数。让我们命名这些 classes

我不确定接口注入是否是我最好的解决方案,因为一旦设置了条件,它很可能永远不会再改变,并且在任何给定时间只能设置一个选项。例如,如果用户决定使用 TestC class,他将更改为其他三个剩余 class 中的任何一个的概率几乎为零。所以,如果我是正确的,如果我使用接口注入(如下例所示)并添加所有四个 classes,我将不必要地实例化 3 个 classes,因为它们很可能永远不会得到使用

public function __constructor(
    SomeInterface $some, 
    AnotherInterface $another,
    TestBInterface $testB,
    TestCInterface $testC,
    TestDInterface $testD,
    TestEInterface $testE
) {
    // Rest of code
}

我想到的是用 $additionalArgs 的 属性 创建我的 TestClassA,创建所需 class 的新实例,假设 [=16] =] 然后将其传递给 $additionalArgs,然后我在方法中使用它来获取所需的值。

例子

$a = new SomeClass;
$b = new AnotherClass;
$c = new TestC;

$d = new TestClassA($a, $b, $c->someMethod());

我的问题是,如何确保传递给 $additionalArgs 的值是应传递给此参数的四个 class 之一的有效实例。我已经尝试在我的方法中使用 instanceof 来验证这一点,在此示例中为 someMethod() ,但条件失败

关于如何解决这个问题的任何建议,并且仍然 "comply" 基本的 OOP 原则?

目前您正在传递一个方法的结果,您无法测试它以查看 class 它来自什么,因此 instanceof 将不起作用。您需要做的是传入对象,对其进行测试,然后调用该方法。试试这个:

class TestClassA() {
    $foo;
    $bar;
    $testB;
    $testC;
    $testD;
    $testE;
    public function __constructor(Foo $foo, Bar $bar, $test = null)
    {
        $this->foo = $foo;
        $this->bar = $bar;
        if ( ! is_null($test))
        {
            if ($test instanceof TestClassB)
            {
                $this->testB = $test->someMethod();
            }
            elseif ($test instanceof TestClassC)
            {
                $this->testC = $test->someMethod();
            }
            elseif ($test instanceof TestClassD)
            {
                $this->testD = $test->someMethod();
            }
            elseif ($test instanceof TestClassE)
            {
                $this->testE = $test->someMethod();
            }
            // Optional else to cover an invalid value in $test
            else
            {
                throw new Exception('Invalid value in $test');
            }
        }
        // Rest of code
    }
}

$a = new Foo;
$b = new Bar;
$c = new TestClassC;

$d = new TestClassA($a, $b, $c);