Warning: Cannot use a scalar value as an array in /home/admin/public_html/forum/include/fm.class.php on line 757

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/include/fm.class.php on line 770

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/topic.php on line 737
Форумы портала PHP.SU :: Наследование методов и их переопределение

 PHP.SU

Программирование на PHP, MySQL и другие веб-технологии
PHP.SU Портал     На главную страницу форума Главная     Помощь Помощь     Поиск Поиск     Поиск Яндекс Поиск Яндекс     Вакансии  Пользователи Пользователи


 Страниц (1): [1]   

> Без описания
Opo6ac
Отправлено: 17 Августа, 2011 - 09:32:12
Post Id


Новичок


Покинул форум
Сообщений всего: 21
Дата рег-ции: Сент. 2009  


Помог: 0 раз(а)




Добрый день.
Помогите разобраться с наследованием и переопределением методов в дочернем классе.

Итак, есть "корневой" класс system. Есть класс afisha, который extends system. И есть класс afisha_cities, который extends afisha.

В "корневом" классе описывается геттер:
PHP:
скопировать код в буфер обмена
  1.   function &__get($name){
  2.     if(property_exists(__CLASS__,$name)){
  3.       return $this->$name;
  4.     } else {
  5.       switch($name){
  6.         case 'users':
  7.           $this->users = $this->read_data('system.users');
  8.           return $this->users;
  9.           break;
  10. ... другие кейсы опустил...

Примечание: существует ряд свойств, которые могут подгружаться различными методами по требованию - для того и нужен геттер, чтобы не лепить множество проверок на существование свойства.

В классе afisha этот геттер переопределяется:
PHP:
скопировать код в буфер обмена
  1.   function &__get($name){
  2.     parent::__get($name);
  3.     switch($name){
  4.       case 'cities':
  5.         $this->cities = $this->get_cities();
  6.         return $this->cities;
  7.       break;
  8.     }
  9.   }

Примечание: в дочернем классе появляются свои свойства, которые нужно подгружать по первому требованию. Но при этом не нужно забывать про старые свойства из system. Именно для этого переопределяя в дочернем классе геттер, я упоминаю родительский геттер и только потом добавляю еще кейсов для автозагрузки.
Примечание: родительский геттер "не закрывается", то есть он или return значение при наличии соответствующего кейса, или ничего не возвращает. Default кейса нет.

Проблема в том, что в экземпляре "третьего поколения" (в afisha_cities, который extends afisha. В нем геттер никак не перегружается, а всего лишь наследуется по умолчанию) не запускаются геттеры из system. Вернее, они запускаются.. но как-то очень странно срабатывают.

если я спрошу:
var_export( $this->user );
то вернется NULL

Но если спросить в такой последовательности:
$this->user;
var_export( $this->user );
то вернется требуемое значение

В общем, помогите понять, где собака зарыта.


Дополнение: геттер однозначно рабочий, он проверялся на другом потомке (как бы второго поколения) system с тем отличием, что в потомке никакой перегрузки геттера не было. Он просто наследовался как обычно и срабатывал, как ожидается.
 
 Top
Opo6ac
Отправлено: 17 Августа, 2011 - 16:31:38
Post Id


Новичок


Покинул форум
Сообщений всего: 21
Дата рег-ции: Сент. 2009  


Помог: 0 раз(а)




Модификацию наследуемого метода в данном случае осуществил так:
PHP:
скопировать код в буфер обмена
  1.   function &__get($name){
  2.     if(parent::__get($name)) return parent::__get($name);
  3.  
  4.     switch($name){
  5.  
  6.       case 'afisha_config':
  7.         return $this->cities;
  8.       break;
  9.     }
  10.   }


Благодарю за внимание.
LEVEL UP! Радость
 
 Top
LIME
Отправлено: 17 Августа, 2011 - 17:01:50
Post Id


Активный участник


Покинул форум
Сообщений всего: 10732
Дата рег-ции: Нояб. 2010  


Помог: 322 раз(а)




а если так?
PHP:
скопировать код в буфер обмена
  1. function &__get($name){
  2.         switch($name){
  3.       case 'cities':
  4.         $this->cities = $this->get_cities();
  5.         return $this->cities;
  6.       break;
  7.     return parent::__get($name);
  8.     }
  9.   }
 
 Top
Opo6ac
Отправлено: 17 Августа, 2011 - 17:44:21
Post Id


Новичок


Покинул форум
Сообщений всего: 21
Дата рег-ции: Сент. 2009  


Помог: 0 раз(а)




LIME, да, можно, в принципе, и так. Тогда и родительский switch можно будет "закрыть" default кейсом, который будет возвращать false - удобно будет для проверки на существование свойства (чтобы isset() не трогать)

Спасибо за свежую мысль) - плюсик поставить не могу, статус не позволяет.

О!... ничего не понял, но сделав предложенную замену, исправил баг, который уже отчаялся сегодня пофиксить. Двойное спасибо!)

(Отредактировано автором: 17 Августа, 2011 - 17:57:19)

 
 Top
Страниц (1): [1]
Сейчас эту тему просматривают: 0 (гостей: 0, зарегистрированных: 0)
« Объектно-ориентированное программирование »


Все гости форума могут просматривать этот раздел.
Только зарегистрированные пользователи могут создавать новые темы в этом разделе.
Только зарегистрированные пользователи могут отвечать на сообщения в этом разделе.
 



Powered by PHP  Powered By MySQL  Powered by Nginx  Valid CSS  RSS

 
Powered by ExBB FM 1.0 RC1. InvisionExBB