Как добавить метод к существующему классу в PHP?

Я использую WordPress в качестве CMS, и я хочу расширить один из его классов, не имея необходимость наследоваться другому классу; т.е. Я просто хочу "добавить" больше методов к тому классу:

class A {

    function do_a() {
       echo 'a';
    }
}

затем:

function insert_this_function_into_class_A() {
    echo 'b';
}

(некоторый способ ввести последнего в класс)

и:

A::insert_this_function_into_class_A();  # b

Это даже возможно в стойком PHP?

18
задан Artefacto 10 June 2010 в 05:52
поделиться

4 ответа

Если вам нужен доступ только к Public API класса, вы можете использовать Decorator:

class SomeClassDecorator
{
    protected $_instance;

    public function myMethod() {
        return strtoupper( $this->_instance->someMethod() );
    }

    public function __construct(SomeClass $instance) {
        $this->_instance = $instance;
    }

    public function __call($method, $args) {
        return call_user_func_array(array($this->_instance, $method), $args);
    }

    public function __get($key) {
        return $this->_instance->$key;
    }

    public function __set($key, $val) {
        return $this->_instance->$key = $val;
    }

    // can implement additional (magic) methods here ...
}

Затем оберните экземпляр SomeClass:

$decorator = new SomeClassDecorator(new SomeClass);

$decorator->foo = 'bar';       // sets $foo in SomeClass instance
echo $decorator->foo;          // returns 'bar'
echo $decorator->someMethod(); // forwards call to SomeClass instance
echo $decorator->myMethod();   // calls my custom methods in Decorator

Если вам нужен доступ к protected API, вы должны использовать наследование. Если вам нужен доступ к private API, вам придется модифицировать файлы классов. Хотя подход с наследованием вполне подходит, модификация файлов классов может вызвать проблемы при обновлении (вы потеряете все сделанные исправления). Но оба варианта более осуществимы, чем использование runkit.

23
ответ дан 30 November 2019 в 07:33
поделиться

Вы можете использовать расширение runkit для этого, но на самом деле вам следует рассмотреть обычное наследование.

See runkit_method_add.

3
ответ дан 30 November 2019 в 07:33
поделиться

Нет, вы не можете динамически изменять класс во время выполнения в PHP.

Вы можете достичь этого, либо расширив класс с помощью обычного наследования:

class Fancy extends NotSoFancy
{
    public function whatMakesItFancy() //can also be private/protected of course
    {
        //    
    }
}

Или вы можете отредактировать исходные файлы Wordpress.

Я бы предпочел способ наследования. С этим намного проще справиться в долгосрочной перспективе.

-1
ответ дан 30 November 2019 в 07:33
поделиться

Если рассматриваемый класс реализует магию __call, то это возможно, и довольно просто. Если вы хотите узнать, как это работает, советую прочитать Расширение объектов новыми методами во время выполнения.

2
ответ дан 30 November 2019 в 07:33
поделиться
Другие вопросы по тегам:

Похожие вопросы: