![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Конструктор [D5, D7, Win2k, WinXP]
Dust © (2005-07-26 11:05:00)Народ, в конструкторе объекта проверяются на правильность переданные параметры. Возможно ли откатить работу конструктора и не вернуть объект, в случае если входные параметры окажутся неверными?
Alexander Panov (2005-07-26 13:02:00) [1]Думкин © (26.07.05 12:47) [23]
А если в предке вызывается исключение в конструкторе?
Ну тогда ничего не поделаешь, если только предок не свой.
Думкин (2005-07-26 12:47:00) [2]> Alexander Panov ©
А если в предке вызывается исключение в конструкторе? Ведь тогда мы до проверки на нил и не дойдем - получим то, что и не хотели - исключение.
Alexander Panov (2005-07-26 12:43:00) [3]Fay © (26.07.05 12:25) [20]
Это дополнительные затраты на блок try..except-)
TMyClass=class
private
FParam: String;
class function CheckParam(const aParam: String): Boolean;
public
constructor Create(const aParam: String);
class function CreateObj(const aParam: String): TMyClass;
end;
class function TMyClass.CheckParam(const aParam: String): Boolean;
begin
Result := (aParam<>'');
end;
constructor TMyClass.Create(const aParam: String);
begin
if not CheckParam(aParam) then raise Exception.Create('Bad parameters format');
FParam := aParam;
end;
class function TMyClass.CreateObj(const aParam: String): TMyClass;
begin
if CheckParam(aParam)
then Result := TMyClass.Create(aParam)
else Result := nil;
end;
Fay (2005-07-26 12:26:00) [4]в смысле
constructor TMyClass.Create(Param : String);
begin
...
8)
Fay (2005-07-26 12:25:00) [5]2 Alexander Panov © (26.07.05 11:56) [17]
В таком случае
TMyClass=class
public
constructor Create(Parm: String);
class function CreateMyObj(Parm: String): TMyClass;
end;
class function CreateMyObj(Parm: String): TMyClass;
begin
try
Result := TMyClass.Create(Parm);
except
Result := nil;
end;
end;
constructor Create(Param : String);
begin
if Param = '' then
raise Exception.Create('Опаньки!');
end;
Плохиш (2005-07-26 12:22:00) [6]
> Ega23 © (26.07.05 12:03) [18]
> насколько я понимаю, всё дело в стиле, а он у каждого -
> свой. Проверять придётся и так и так. Только в одном случае
> это будет
Ну дык :-)
try
MyObj:=TMyObj.Create(Param);
try
.....
finally
MyObj.Free;
end;
except
on E:Exception do ShowMessage('Not Created: ' + E.Message);
end;
Ega23 (2005-07-26 12:03:00) [7]насколько я понимаю, всё дело в стиле, а он у каждого - свой. Проверять придётся и так и так. Только в одном случае это будет
try
MyObj:=TMyObj.Create(Param);
try
.....
finally
MyObj.Free;
end;
except
ShowMessage('Not Created')
end;
А в другом
MyObj:=TMyObj.CreateEx(Param);
if not Assigned(MyObj) then
begin
ShowMessage('Not Created');
Exit;
end;
try
......
finally
MyObj.Free;
end;
Alexander Panov (2005-07-26 11:56:00) [8]Плохиш © (26.07.05 11:50) [16]
Ну вот представь - не хочу я возбуждать исключение при создании объекта. Для этого как раз и использую классовую функцию, где происходит проверка параметров. Если параметры ошибочны - объект не создается.
Но чтобы можно было воспользоваться и стандартным конструктором, нужно и в нем проверять параметры. И в этом случае без исключения уже не обойтись.
Так что этот подход ничем не отличается от стандартного-)
Плохиш (2005-07-26 11:50:00) [9]
> Alexander Panov © (26.07.05 11:46) [14]
> А для этого нужно еще и в конструкторе проверять параметры
> и возбуждать исключение-)
Хм, всегда считал, что это одна из задач конструктора :o)
Плохиш (2005-07-26 11:48:00) [10]IMHO. Если объект не может быть создан, в конструкторе должно быть возбуждено соответствующее исключение, дающее исчерпывающую информацию о причине невозможности.
Alexander Panov (2005-07-26 11:46:00) [11]Юрий Зотов © (26.07.05 11:45) [12]
Если нужна надежность - надо перекрывать конструктор и вызывать в нем исключение. Только так и никаких class function. Потому что стоит прикладному программисту (по незнанию тонкостей проекта или по забывчивости) создать объект обычным, привычным образом - и кирдык.
А для этого нужно еще и в конструкторе проверять параметры и возбуждать исключение-)
Думкин (2005-07-26 11:45:00) [12]пропустил - каюсь
Юрий Зотов (2005-07-26 11:45:00) [13]> Fay © (26.07.05 11:35) [9]
Смайлик видели?
:о)
Если нужна надежность - надо перекрывать конструктор и вызывать в нем исключение. Только так и никаких class function. Потому что стоит прикладному программисту (по незнанию тонкостей проекта или по забывчивости) создать объект обычным, привычным образом - и кирдык.
jack128 (2005-07-26 11:40:00) [14]Думкин © (26.07.05 11:38) [10]
Ровно также как и везде где он создается придется проверять на nil.
В чем выигрыш?
как раз не давно ветка была 'if vs try except' ...
Думкин (2005-07-26 11:38:00) [15]> Но тогда его надо обрабатывать везде, где создается объект.
> А можно и методом вызова классовой функции, которая вернет
> nil. ТОгда исключение возникать не будет. Достаточо проверить
> на nil, и все.
>
> MyObj := TMyClass.CreateMyObj('');
> if Assigned(MyObj) then ...
Ровно также как и везде где он создается придется проверять на nil.
В чем выигрыш?
Fay (2005-07-26 11:35:00) [16]2 Юрий Зотов © (26.07.05 11:33) [7]
Такая мысль возникает сразу, но если параметров много, то вид [2] может оказаться читабельнее.
Fay (2005-07-26 11:34:00) [17]2 Alexander Panov © (26.07.05 11:32) [6]
[5] -> 1)...
Юрий Зотов (2005-07-26 11:33:00) [18]Код в [2] записывается проще, без всяких class function:
if Parm = '' then R := nil else R := TMyClass.Create(Parm);
:о)
Alexander Panov (2005-07-26 11:32:00) [19]Fay © (26.07.05 11:24) [3]
Можно возбуждать исключение. Но тогда его надо обрабатывать везде, где создается объект.
А можно и методом вызова классовой функции, которая вернет nil. ТОгда исключение возникать не будет. Достаточо проверить на nil, и все.
MyObj := TMyClass.CreateMyObj('');
if Assigned(MyObj) then ...
Fay (2005-07-26 11:32:00) [20]2 Ega23 © (26.07.05 11:25) [4]
Если
1) для проверки не требуется функциональность целевого класса
2) желательно избежать исключений
, то можно и попробовать.