有没有办法在静态方法中检测目标类?

时间:2008-09-17 14:34:48

标签: php oop php-5.3 php-5.2

下面是一个示例类层次结构和代码。我正在寻找的方法是确定'ChildClass1'或'ChildClass2'是否具有静态方法whoAmI()调用它而不在每个子类中重新实现它。

<?php

abstract class ParentClass {

    public static function whoAmI () {

        // NOT correct, always gives 'ParentClass'
        $class = __CLASS__;

        // NOT correct, always gives 'ParentClass'. 
        // Also very round-about and likely slow.
        $trace = debug_backtrace();
        $class = $trace[0]['class'];

        return $class;
    }
}

class ChildClass1 extends ParentClass {

}

class ChildClass2 extends ParentClass {

}

// Shows 'ParentClass'
// Want to show 'ChildClass1'
print ChildClass1::whoAmI(); 
print "\n";

// Shows 'ParentClass'
// Want to show 'ChildClass2'
print ChildClass2::whoAmI();
print "\n";

5 个答案:

答案 0 :(得分:7)

我相信你所指的是一个已知的php bug。 Php 5.3旨在通过新的Late Static Binding功能来解决这个问题。

http://www.colder.ch/news/08-24-2007/28/late-static-bindings-expl.html

答案 1 :(得分:2)

类别识别通常是未被充分理解的多态性的症状。

ChildClass1和ChildClass2的客户端不应该区分它们。

任何班级都不应该问someObject.whoAmI()

每当你有写if someObject.whoAmI() == 'ChildClass1' { do X(someObject) }的冲动时,你应该在ParentClass中添加一个X()方法,并在各种ChildClasses中使用各种实现。

这种“运行时类型识别”几乎总能被适当的多态类设计所取代。

答案 2 :(得分:2)

现在PHP 5.3在野外广泛使用,我想整理一个这个问题的摘要答案,以反映新的技术。

正如其他答案所述,PHP 5.3通过新的Late Static Binding关键字引入了static。同样,还可以使用新的get_called_class()函数,该函数只能在类方法(实例或静态)中使用。

为了确定此问题中提到的课程,get_called_class()函数是合适的:

<?php

abstract class ParentClass {

    public static function whoAmI () {
        return get_called_class();
    }

}

class ChildClass1 extends ParentClass {

}

class ChildClass2 extends ParentClass {

}

// Shows 'ChildClass1'
print ChildClass1::whoAmI(); 
print "\n";

// Shows 'ChildClass2'
print ChildClass2::whoAmI();
print "\n";

user contributed notes for get_called_class()包括一些应该在PHP 5.2中使用的示例实现,并使用debug_backtrace()

答案 3 :(得分:1)

从PHP 5.3开始,可以使用static keyword,但现在不可能。

答案 4 :(得分:0)

没有。等待PHP 5.3。