将子 classes 分配给父 class 中的变量

Assigning child classes to a variable in parent class

我有这些相关的 classes:

class cars {

    public $cars;

    public function addCar($name, $car)
    {
        $this->cars[$name] = $car;
    }

    public function getCars()
    {
        return $this->cars;
    }

    public function getCar($name)
    {
        return $this->cars[$name];
    }

    public function getParams()
    {
        return $this->params;
    }
}

$cars = new cars();

class bmw extends cars {

    private static $_instance = null;
    protected $params;

    function __construct()
    {
        $this->params['param'] = 'foo';
    }

    public static function init()
    {
        if (self::$_instance === null) {
            self::$_instance = new self;
        }

        return self::$_instance;
    }
}

$cars->addCar( 'bmw', bmw::init() );

基本上我需要从父 class 访问所有子 classes。并在定义的子 class 上使用父 class 中定义的方法。添加新子 classes 时不应修改父 class。

最后应该是这样的:

foreach( $cars->getCars() as $car )
{
    foreach( $car->getParams() as $key => $param )
        echo "$key = $param";
}

执行此操作的正确方法是什么?

提供帮助真的很困难,因为您不太清楚您要实现的目标。

在我看来,您需要 Registry Class (carDealer),一个抽象 class 具有通用(对于每个子项)方法和一个子项 (Bmw)。

所以,类似于:

// You seems to need what is called sometimes a Registry. 
// Something which deal with keeping and delivering a group of 'related' classes, as a register.
class CarsDealer
{
    public $cars;

    public function addCar($name, $car)
    {
        $this->cars[$name] = $car;
    }

    public function getCars()
    {
        return $this->cars;
    }

    public function getCar($name)
    {
        return $this->cars[$name];
    }
}

// then you need a basic contract for each concrete classes 
// that will have the same nature and so will extend it 
abstract class Car
{
    protected $params;

    public function getParams()
    {
        return $this->params;
    }
}

// finally the concrete class
class Bmw extends Car
{
    public function __construct($params = null)
    {
        $this->params['param'] = $params;
    }
}

$carsDealer = new CarsDealer();

$carsDealer->addCar('bmw', new Bmw('foo'));

foreach ($carsDealer->getCars() as $car)
{
    foreach ($car->getParams() as $key => $param) {
        echo "$key = $param";
    }
}

请注意一些基本的rules/good practices/conventions:

另一种方法,如果你只需要得到这个 'params' :-)

class cars {

    public $cars;

    public function addCar($name, $car)
    {
        $this->cars[$name] = $car;
    }

    public function getCars()
    {
        return $this->cars;
    }

    public function getCar($name)
    {
        return $this->cars[$name];
    }

    public function getParams($obj)
    {
        return $obj->params;
    }


}

$cars = new cars();

class bmw extends cars {

    private static $_instance = null;
    protected $params;

    function __construct()
    {
        $this->params['param'] = 'foo';
    }

    public static function init()
    {
        if (self::$_instance === null) {
            self::$_instance = new self;
        }

        return self::$_instance;
    }
}

$cars->addCar( 'bmw', bmw::init() );

print_r( $cars->getParams($cars->getCar('bmw')));