Я создал абстрактный родительский класс и конкретный класс, который его расширяет. Почему родительский класс не может назвать абстрактную функцию?
//foo.php <?php abstract class AbstractFoo{ abstract public static function foo(); public static function getFoo(){ return self::foo();//line 5 } } class ConcreteFoo extends AbstractFoo{ public static function foo(){ return "bar"; } } echo ConcreteFoo::getFoo(); ?>
Ошибка:
Неустранимая ошибка: не удается вызвать абстрактный метод AbstractFoo :: foo () в foo.php в строке 5
Это правильная реализация; вы должны использовать static, а не self, чтобы использовать поздние статические привязки :
abstract class AbstractFoo{ public static function foo() { throw new RuntimeException("Unimplemented"); } public static function getFoo(){ return static::foo(); } } class ConcreteFoo extends AbstractFoo{ public static function foo(){ return "bar"; } } echo ConcreteFoo::getFoo();
дает ожидаемый «бар».
Обратите внимание, что это не полиморфизм. Статический ключ работает только в классе, из которого был вызван статический метод. Если вы объявите абстрактный статический метод, вы получите строгое предупреждение. PHP просто копирует все статические методы из родительского (супер) класса, если они не существуют в дочернем (дочернем) классе.
Вы замечаете это слово « self
?
Это указывает на AbstractClass. Таким образом, он вызывает AbstractClass :: foo (), а не ConcreteClass :: foo ();
Я полагаю, что PHP 5.3 обеспечит поздние статические привязки, но если вы не используете эту версию, я не буду ссылаться на расширенный класс, а на класс, в котором находится функция.
См .: http://us.php.net/manual/en/function.get-called-class.php
Правило состоит в том, что abstract
и static
ключевые слова нельзя использовать одновременно.
Метод с ключевым словом abstract
означает, что подкласс должен его реализовать. Добавление static в метод класса позволяет использовать метод без его создания.
Вот почему возникает ошибка.