PHP:声明一个类变量为stdClass对象

18

这可能很简单,但我一直没有想出如何在Google上提出问题,所以我来试试:

我经常做这样的事情...

class foo {
    private $bar = array();
}

...设置类属性为数组,但我想将一个私有属性改为对象,就像这样:

class foo {
    private $bar = new stdClass();
}

我尝试了几种变化,但它们都没有起作用。这能做到吗?如果您能将私有属性分配给任何其他类对象,则可获得额外的奖励分数。

谢谢!

1个回答

25

在类成员声明中,您不能使用函数(包括构造函数)。相反,应在类的构造函数中设置。

class Foo {

  private $bar;

  private $baz;

  public function __construct() {

    $this->bar = new stdClass();
    $this->baz = new Bat();

  }

  public function __get($key) {
      if(isset($this->$key) {
        return $this->$key;
      }

      throw new Exception(sprintf('%s::%s cannot be accessed.', __CLASS__, $key));
  }

}


$foo = new Foo();

var_dump($foo->bar);
var_dump($foo->bat);

当你扩展一个类并需要重写构造函数,但仍希望使用父类构造函数中的内容时:

class FooExtended
{
   protected $coolBeans;

   public function __construct() {

      parent::__construct(); // calls the parents constructor

      $this->coolBeans = new stdClass();
   }
}

$foo = new FooExtended();

var_dump($foo->bar);
var_dump($foo->bat);
var_dump($foo->coolBeans);

需要注意的是,这与属性的可见性无关... 这不受其protectedprivatepublic的影响。


好的,那个有效。但是,如果我希望这个类可以被其他类扩展并可能覆盖构造函数怎么办?有没有办法确保 $bar 仍然是一个对象? - Andrew
请查看我的注释编辑...并且阅读类和对象手册:http://php.net/manual/zh/language.oop5.php - prodigitalson
感谢这个详细的例子,我看懂你是怎么实现的。我希望能像声明数组那样简单地声明对象。这将使我的代码更加“防傻”,我不喜欢要求用户调用父构造函数,因为他们似乎总是会忘记,并且无法弄清楚为什么事情不能正常工作。然而,有时候你必须得做你应该做的事情。感谢你的帮助! - Andrew
大多数人会知道怎么做...... 如果他们不知道,那就说明他们对面向对象的 PHP 不是很熟悉,这并不是你的错 :-) 此外,您还可以添加获取器来创建对象(如果它尚未初始化)。 - prodigitalson
1
当您扩展父类时,所有子类都应该获得您的stdclass对象。如果您不希望其他人覆盖它,可以在父类中将其声明为私有,然后使用“final”关键字来获取和设置对象变量,这样$bar将保持为一个对象。希望这可以帮助到您。 - vito huang

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接