【问题标题】:PHP / Prado property 'treatment'PHP / Prado 属性“处理”
【发布时间】:2010-12-17 08:10:43
【问题描述】:

我正在学习 Prado php 框架有一段时间了,我一直在想一个特性,它是来自 PHP 还是在 Prado 中以某种方式实现的。

也就是说,Prado 中使用的类可以利用未在类本身中声明但由 set 和 get 方法“定义”的属性(字段)。

这是一个例子:

class myClass extends somePradoClass {

    public function myPradoMethod() {
        $MyVariable = 22;
        echo $MyOtherVariable; // this one is read only (only get method defined)
    }

    public function getMyVariable() {
        return 0;
    } 

    public function setMyVariable($value) {
        $this->isFieldFromParentClass = $value;
    }

    public function getMyOtherVariable() {
        return $this->isOtherFieldFromParentClass;
    }

}

现在,不知何故,在整个类中使用 $MyVariable 和 $MyOtherVariable 是完全没问题的,就好像它们被声明为类属性一样。

那么,再次提问:这是 PHP 还是 Prado 的功能?

谢谢

【问题讨论】:

  • 对我来说听起来很奇怪,我认为它至少不是你想的那样有效。
  • 同意:),我也很困惑……但它以某种方式起作用,我想知道如何:)

标签: php oop prado


【解决方案1】:

这既不是 PHP 功能也不是 Prado 功能。 我不知道普拉多,但是PHP没有这个功能,所以普拉多也没有;)

但是,您正在寻找的是这样的东西:$this->myUndefinedMember = $something

您的示例使用局部变量,这些无法自动设置和读取。

这将调用神奇的__set 方法(如果已定义)。

Prado 可以(我不知道是否)为您通常使用的某个超类定义此方法,然后动态检查是否已为该变量名称定义了 setter 方法。

签名如下:

public function __set($name, $value)

maigc 方法__get($name) 的工作原理类似。

如果您不将其设置为公开,则您将只能在类(或子类)中使用此类似属性的功能。

作为参考,请参阅here 了解 PHP5 的特性或重载属性和方法。

更新

示例实现可能如下所示:

class MyMagicSuperClass{
    public function __get($name){
        $getter_name = 'get'.ucwords($name);
        if(method_exists($this, $getter_name){
            return $this->$getter_name();
        }

        //error handling
    }

    public function __set($name, $value){
        $setter_name = 'get'.ucwords($name);
        if(method_exists($this, $setter_name){
            return $this->$setter_name($value);
        }

        //error handling
    }
}

【讨论】:

  • 查看 OP 代码中的方法,我认为有问题的魔术方法是 __call()。局部变量从不调用__get()__set(),它们与类属性不同。
  • 看看前三段 :) (我编辑了第三段以使事情更清楚,所以你可能已经忽略了) - 但是,__call() 不会被调用,因为他从未真正明确地调用过某些东西。
  • 谢谢你们的回答。我也喜欢示例实现。 PHP 是一门狂野的语言 :)
  • 呵呵,不客气,我也听说 PHP 是“始终不一致,在阅读了这篇不错的(德语)文章后,我同意呵呵blog.benny-baumann.de/?p=334
【解决方案2】:

我很晚才回答这个问题,但我觉得答案对一个简单的功能非常混乱。

给出一个更简单的答案。任何从 TComponent 继承的 Prado 类都使用 __set 和 __get 函数。

更多关于php魔术函数here

所以如果你有一个以“get”或“set”开头的函数,当使用函数名的其余部分作为字段时,它们将被调用。

这是 __get 的实际 prado 代码,__set 大致相同

    public function __get($name)
{
    $getter='get'.$name; $jsgetter = 'getjs'.$name;
    if(method_exists($this,$getter))
    {
        // getting a property
        return $this->$getter();
    }
    else if(method_exists($this,$jsgetter))
    {
        // getting a property
        return (string)$this->$jsgetter();
    }
    else if(strncasecmp($name,'on',2)===0 && method_exists($this,$name))
    {
        // getting an event (handler list)
        $name=strtolower($name);
        if(!isset($this->_e[$name]))
            $this->_e[$name]=new TList;
        return $this->_e[$name];
    }
    else
    {
        throw new TInvalidOperationException('component_property_undefined',get_class($this),$name);
    }
}

【讨论】:

    猜你喜欢
    • 2016-11-19
    • 2016-02-11
    • 2017-11-07
    • 2011-10-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-02-18
    • 2010-11-01
    相关资源
    最近更新 更多