PHP获取子类方法

时间:2014-04-01 10:12:03

标签: php oop

在PHP中是否可以在child类中声明的方法中获取扩展parent类的方法?

这是一个简单的(可能是愚蠢的)示例:

<?php

class Vehicle{
    protected function moveForward(){
        // go ahead...
    }// moveForward

    public function getWhatCanIDo(){
        $actions = get_class_methods($this);
        return 'I can '.implode(', ', $actions).'<br/>';
    }// getWhatCanIDo
}


class Car extends Vehicle{
    protected function honk(){
        // honk...
    }// honk

    protected function turnHeadlightsOn(){
        // turn headlights on...
    }// turnHeadlightsOn

    protected function stopEngine(){
        // stop the engine
    }// stopEngine
}


class Submarine extends Vehicle{
    protected function submerge(){
        // sink...
    }// submerge

    protected function ping(){
        // ping...
    }// ping

    protected function fireTorpedos(){
        // DESTROY!!!
    }// fireTorpedos

    protected function stopEngine(){
        // stop the engine
    }// stopEngine
}


$volvo = new Car();
$uboat = new Submarine();

echo $volvo->getWhatCanIDo();
echo $uboat->getWhatCanIDo();

?>

我期望的输出是:

I can moveForward, getWhatCanIDo, honk, turnHeadlightsOn, stopEngine
I can moveForward, getWhatCanIDo, submerge, ping, fireTorpedos, stopEngine

但是它只返回Vehicle类的方法,而没有在扩展类中实现的方法:

I can moveForward, getWhatCanIDo
I can moveForward, getWhatCanIDo

我怎样才能获得extanded类方法?

其他信息: 我必须在PHP 5.2.14中解决这个问题 扩展类将具有不同数量的具有不同方法名称的方法,因此使Vehicle抽象类不会有帮助,因为例如:我不希望Submarine具有honk方法。 我知道我可以使getWhatCanIDo()成为一个抽象方法,但我想在父类中“集中”实现这个方法,我不想让开发人员为每个扩展类编写getWhatCanIDo()方法(将来其他人可能会加入或继续这个项目,并且更不安全的是不要让他们一次又一次地实现这个方法,特别是当方法完全相同时。)

5 个答案:

答案 0 :(得分:1)

你应该声明class Vehicle摘要,因为它并不存在,真正的车辆实现它。

然后将whatCanIDo放在CarSubmarine中,因为你不会问车辆能做什么,你会问车。

class Car extends Vehicle{
    public function getWhatCanIDo(){
        $actions = get_class_methods($this);
        return 'I can '.implode(', ', $actions).'<br/>';
    }// getWhatCanIDo
}

<强>更新

一种不同的方法是使用标准PHP库 ReflectionClass

$class   = new ReflectionClass('Vehicle');
$methods = $class->getMethods();

答案 1 :(得分:0)

您需要重载Car&amp;中的getWhatCanIDo()功能。潜艇类。您获得输出,因为该函数在Vehicle类中执行。

重载方法会导致它在Car或Submarine类中执行。

答案 2 :(得分:0)

您还可以在http://www.php.net/manual/en/function.get-class-methods.php

尝试get_class_methods();更多内容

答案 3 :(得分:0)

此代码未经过测试,请告诉我它是否有效。

class MyBaseClass {
    //...
    public function getMethods($className) {
        return get_class_methods($className);
    }

    public static function getMethods($myObject) {
        return $myObject->getMethods(get_class($myObject));
    }
    //...
}

class MyInheritedClass {
    //...
}

$myBaseObject = new MyBaseClass(/*...*/);
$myInheritedObject = new MyInheritedClass(/*...*/);
echo var_dump(MyBaseClass::getMethods($myBaseObject));
echo var_dump(MyBaseClass::getMethods($myInheritedObject));

答案 4 :(得分:0)

继承不是适当的工具。你应该使用作文。例如:

  1. 有单独的对象Runner,Swimmer,W​​orkWithEngine,Submerge。所有这些都实现了与getWhatCanIDo()方法的接口。

  2. 通过从第一点的类型中创建新的Vehiclas来创建它。该对象也实现了与getWhatCanIDo()方法的接口。

  3. $submarine = new Submarine(); $submarine->addAblility(new Swimmer()); $submarine->addAblility(new WorkWithEngine()); $submarine->addAblility(new Submerge()); $submarine->whatCanIDo();

    在任何情况下都不要使用像get_class_method这样的魔法,这些是框架创建者的构造,它不是编码业务逻辑的东西。