【问题标题】:How to programmatically find public properties of a class from inside one of it's methods如何以编程方式从其中一个方法中查找类的公共属性
【发布时间】:2012-10-18 21:52:55
【问题描述】:

我有一个类 Foo 具有公共和受保护的属性。 Foo 需要有一个非静态方法getPublicVars(),它返回Foo 的所有公共属性的列表(这只是一个例子,我从Foo 外部知道调用get_object_vars() 的对象将完成此操作,并且不需要我的getPublicVars() 方法。

注意:这还必须返回在运行时分配给类实例(对象)的动态声明的属性,这些属性未在类的定义中定义。

示例如下:

class Foo{
    private $bar = '123';
    protect $boo = '456';
    public   $beer = 'yum';

   //will return an array or comma seperated list
   public function getPublicVars(){
      // thar' be magic here...
   } 
}

 $foo = new Foo();
 $foo->tricky = 'dynamically added var';

 $result = $foo->getPublicVars();  
 var_dump($result); // array or comma list with 'tricky' and 'beer'   

从类自己的方法中获取对象的唯一公共属性的最简洁方法是什么,其中公共和受保护都是可见的?

我看过:

但这似乎并没有解决我的问题,因为它指向从对象外部使用get_object_vars()

【问题讨论】:

    标签: php oop reflection


    【解决方案1】:

    正如您已经意识到的,PHP 在get_object_vars 中的构建是范围敏感的。您只需要 public 对象属性。

    所以从那个函数到公共变体并不是很大的一步:

    function get_object_public_vars($object) {
        return get_object_vars($object);
    }
    

    调用此get_object_public_vars 将只为您提供公共属性,因为它超出了当前对象的范围。

    如果需要更细粒度的控制,也可以使用ReflectionObject

    (new ReflectionObject($this))->getProperties(ReflectionProperty::IS_PUBLIC);
    

    这样做的好处是您不需要在全局命名空间中引入其他函数。

    【讨论】:

    【解决方案2】:

    根据this article(由 Vance Lucas 编写),您可以使用“anonymous”函数在“Foo”类定义中创建一个新的调用范围,然后您可以调用@987654322 @ 从内部。这允许您从您的类内部获取公共属性,即使这些是后来从外部动态创建的。

    所以适应你的例子是:

    <?php
    class Foo {
        private $bar = '123';
        protected $boo = '456';
        public   $beer = 'yum';
    
       // return an array of public properties 
       public function getPublicVars(){
          $publicVars = create_function('$obj', 'return get_object_vars($obj);');
            return $publicVars($this);
       } 
    }
    
     $foo = new Foo();
     $foo->tricky = 'dynamically added var';
    
     $result = $foo->getPublicVars();  
     print_r($result);
    

    输出将是:

    大批 ( [啤酒] => 好吃 [棘手] => 动态添加的 var )

    上面提到的文章中有第二个例子,它展示了另一种使用所谓的“闭包”(来自 php 5.3)来做同样事情的方法,但由于某种原因,它不适用于 php v5.4所以私有和受保护的属性仍然包含在结果数组中。

    【讨论】:

      【解决方案3】:

      不适用于 php 版本 >=7
      因此,我真的不能再推荐解决方案了。
      改用反射

      从类中获取公共属性

      $publicProperties = call_user_func('get_object_vars', $this);
      

      “诀窍”是从 call_user_func 的范围而不是对象的范围调用 get_object_vars

      不需要反射、独立函数、闭包等

      【讨论】:

      • 谢谢,恕我直言,这是最好的答案,因为get_object_vars 将返回受保护和私有属性,如果在同一类中使用,如pastebin.com/FjqzYvLC
      • 不适用于 php 版本 >=7 看起来这依赖于 php 7 中修复的错误。虽然在撰写本文时是一个有效的答案,但它是使用它不再是一个好主意 - 改用ReflectionObject
      猜你喜欢
      • 2013-09-13
      • 1970-01-01
      • 1970-01-01
      • 2018-11-06
      • 2012-06-26
      • 2020-09-25
      • 1970-01-01
      • 1970-01-01
      • 2022-08-15
      相关资源
      最近更新 更多