1

我的团队正在使用延迟加载技术从我们的数据库中加载子对象。为此,我们使用神奇的 __get() 方法并进行数据库调用。我们所有的属性都受到保护,所以 __get 方法是从对象外部调用的,但我们的问题是它不会在不使用的情况下从对象内部调用$this->__get($name);

所以我的问题是:是否可以强制 __get() 使用正常的链接运算符甚至从对象内部调用?

如果我想链接对象访问,我目前必须这样做:

$this->__get('subObject')->__get('subObject')->__get('subObject') 

是否可以编写以下内容,但仍然调用 __get()?

$this->subObject->subObject->subObject

谢谢,乔丹

4

2 回答 2

1

约旦,

PHP 不会调用该__get()方法,除非该属性不可访问——要么是因为它不存在,要么是因为可见性。当属性在调用范围内隐藏时,会调用 __get() 方法,因为该属性不可访问。当属性被引用并且可用于调用范围时,__get() 将永远不会触发。(这并不意味着为现有/可访问的财产开火。)

要解决此问题,您必须重命名内部属性。要么为它们加上一个名称、下划线,要么将它们存储在一个具有特殊名称的公共数组参数中。以下内容有些人为,但它应该展示您如何处理这种情况。

class MyObject {
   protected $lazyloads = array();

   protected function lazyload($relation) {
     // ...
   }

   public function __get($key) {
     if (isset($this->lazyloads[$key]) {
       return $this->lazyloads[$key];
     } else {
       return $this->lazyload($key);
     }
   }
}

见:http ://www.php.net/manual/language.oop5.overloading.php#object.get

于 2013-03-22T15:46:30.413 回答
0

@Robert K 或者(例如):

class A
{
    protected $objects = array();

    public function __get($name)
    {
        if(isset($this->objects[$name])) {
            return $this->objects[$name];
        }
        return null; // or throw \Exception
    }
}
class B
{
    protected $objects = array();

    public function __get($name)
    {
        // for example: $this->objects[$name] is type of A
        if(isset($this->objects[$name])) {
            return $this->objects[$name];
        }
        return null; // or throw \Exception
    }
}

每个返回的对象都必须有一个返回对象的魔术方法__get

于 2013-03-22T15:48:55.367 回答