приведение объекта к другому классу из его иерархии

Foror

Новичок
приведение объекта к другому классу из его иерархии

class Test {}
class Test2 extends Test {}

$t = new Test();
$t = (Test2)$t;

Такое естно не работает. Есть выход?
 

Krishna

Продался Java
Налицо неправильный подход в применении ООП :)
Напиши конкретно какую задачу ты решаешь и в чем загвоздка.

-~{}~ 08.02.06 09:47:

Почему просто нельзя сделать $t = new Test2(); ?
 

Foror

Новичок
Я хочу добавить к классу Exception, кое-какой метод. И соотвественно мне нужно, чтобы все наследники этого класса имели этот метод. Конечно можно сделать наследника от Exception и потом все должны будут наследовать этот новый класс, но это как-то не очень мне нравится.

Как я хотел(и сейчас понял что это не очень круто) сделать класс ExceptionForLog, который будет содержать этот заветный метод, и все ексепшены приводить к этому классу. Но если так делать, то можно потерять специфичные для некоторых ексепешнов поля и методы.

Я вот тут еще думал(и сейчас мне эта идея начинает нравится больше) сделать Обёртку вот так:

class ExceptionWrapper
{
protected $exception;

public function setException(Exception $e)
{
$this->exception = $e;
}

public function MySpecMethod()
{
// работаем с $this->exception;
}
}
 

Krishna

Продался Java
Конечно можно сделать наследника от Exception и потом все должны будут наследовать этот новый класс, но это как-то не очень мне нравится.
Чем не нравится? Почему "и потом все должны будут наследовать"? Результирующие объекты будут отличных классов от "ExceptionForLog"?
 

Foror

Новичок
Если в проект я добавлю либы не моего производства, то они соответсвенно не будут наследовать MyException, а будут наследовать Exception, а значит часть ексепшенов у меня будут логироваться, а дргуая часть не будет.

А мне нужно, чтобы все exception логировались
 

whirlwind

TDD infected, paranoid
class Test {}
class Test2 extends Test {}

$t = new Test();
$t = (Test2)$t;
PHP:
class Test{
   protected function someMethod(){
      // базовая реализация
   }
}

class Test2 extends Test{
    // унаследовали оригинальный someMethod
}

class Test3 extends Test{
    protected function someMethod(){
        // неустраивает базовая реализация, переопределям
    }
}


$t2 = new Test2;
$t2->someMethod(); // метод базового класса
$t3 = new Test3;
$t3->someMethod(); // переопределенный вариант
-~{}~ 08.02.06 11:42:

Если в проект я добавлю либы не моего производства, то они соответсвенно не будут наследовать MyException, а будут наследовать Exception, а значит часть ексепшенов у меня будут логироваться, а дргуая часть не будет.
значит надо не экспкшены оборачивать, а унифицировать способ их обработки
 

Foror

Новичок
Вот как сделано(черновик) это у меня сейчас:

Как это работает:
PHP:
...
catch (Exception $e)
{
    new Log($e)
}
PHP:
class Log
{
    // $data - Exception, Error ...
    public function __construtc($data)
    {
         ....
         
         // $output - LogXmlOutput, LogHtmlOutput ...
         $output->append($data)
    }
}

class LogXmlOutput extends LogOutput {}
class LogHtmlOutput extends LogOutput {}

class LogOutput
{
      public function append($data)
      {
        $nameMethod = "createOutputData";
        
        if (($data instanceof Exception) || is_subclass_of($data, 'Exception')) {
            $data = (ExceptionToLog)$data;
        }
        
        if (method_exists($data, $nameMethod))
        {
           $this->outputData = $data->createOutputData();
        }
        else 
        {
            $dataClass = get_class($data);
            throw new LogOutputException(_("Класс \"$dataClass\" не поддерживает метод \"$nameMethod\""));
        }
      }
}
 

whirlwind

TDD infected, paranoid
я бы так сделал

PHP:
// с оберткой
$w = new ExceptionWrapper;
$w->runWrapped(new SomeController);

// ручная обработка исключений

try{
   $c = new SomeController;
   $c->run();
}catch(Exception $e){

}catch ...
Контроллер не заморачивается исключениями, обертка не заморачивается контроллером - знает только что запустить контроллер можно методом run и умеет обрабатывать те исключения, что заложены программистом. Надо будет расширить - просто наследуем враппер и добавляем туда механизмы обработки новых исключений. А там что угодно, хоть в лог, хоть на мыло и все это малой кровью - реализовано в базовом классе... Естессно это не прокатит, если специфика приложения в виде модульной портянки, но это уже из другой оперы.

-~{}~ 08.02.06 13:04:

Кстати, насчет объекта-лога. Я бы не стал пихать в лог обработку ошибочных ситуаций. Лог - это только механизм работы с логом. Ни больше, ни меньше. Инкапсулировать надо его во враппере исключений, а не перегружать иерархию левыми методами.

-~{}~ 08.02.06 13:11:

PS. еще о логе. Тогда это выглядело бы так

PHP:
$l = new LogXmlOutput;
$w = new ExceptionWrapper;
$w->setLog($l); // любого типа лог!!!
...
 
Сверху