Форум: "Начинающим";
Текущий архив: 2008.06.08;
Скачать: [xml.tar.bz2];
ВнизОсвобождение ресурса в finally Найти похожие ветки
← →
{RASkov} © (2008-04-24 10:59) [40]> [36] ANB (24.04.08 10:31)
> это написать и корректно и читабельно ?
Obj1 := TObj.Create;
try
Obj2 := TObj.Create;
try
Obj3 := TObj.Create;
try
Obj4 := TObj.Create;
try
Obj5 := TObj.Create;
try
...
работа с объектами и куча другого кода
finally
FreeAndNil(Obj5);
end;
finally
FreeAndNil(Obj4);
end;
finally
FreeAndNil(Obj3);
end;
finally
FreeAndNil(Obj2);
end;
finally
FreeAndNil(Obj1);
end;
или при уверенности, что в конструкторе не будет ошибок, то:
Obj1 := TObj.Create;
Obj2 := TObj.Create;
Obj3 := TObj.Create;
Obj4 := TObj.Create;
Obj5 := TObj.Create;
try
...
работа с объектами и куча другого кода
finally
FreeAndNil(Obj1);
FreeAndNil(Obj2);
FreeAndNil(Obj3);
FreeAndNil(Obj4);
FreeAndNil(Obj5);
end;
Но если честно, то у меня такого в коде никогда еще не встречалось :)
← →
ZENsan © (2008-04-24 11:16) [41]Удалено модератором
← →
Arinyshka (2008-04-24 11:28) [42]А мне велено почитать про секцию finalization. Может, так действительно проще?
инициализировать и освободить в соотв секциях...
Из советов мне понятен вариант с проверкой:f Assigned(Obj1) then
i
Obj1.Free;
тогда я никого не попытаюсь освободить дважды
← →
ZENsan © (2008-04-24 11:31) [43]Да делай именно так Аринишка - стандартный подход. Можно конечно и в секциях - так лучше если ты используеш этот код очень часто (не будешь каждый раз создавать и удалять объект..)
← →
{RASkov} © (2008-04-24 11:33) [44]> [42] Arinyshka (24.04.08 11:28)
> f Assigned(Obj1) then
> Obj1.Free;i
> тогда я никого не попытаюсь освободить дважды
Не факт. Смотри:
Obj1:=TObj.Create;
f Assigned(Obj1) then Obj1.Free;
f Assigned(Obj1) then Obj1.Free;
И тут АВ на второй строке.
Правильно так:
Obj1:=TObj.Create;
f Assigned(Obj1) then begin Obj1.Free; Obj1:=nil; end;
f Assigned(Obj1) then begin Obj1.Free; Obj1:=nil; end; //не будет АВ
ну или Freeandnil()...
← →
ZENsan © (2008-04-24 11:34) [45]Ну ето понятноъъъ Но мы же вроде про один блок Try Finally...
Там тогда просто надо:
If Assigned(Obj1) then
FreaAndNil(Obj1);
← →
{RASkov} © (2008-04-24 11:39) [46]> [45] ZENsan © (24.04.08 11:34)
А смысл? не вижу...(
Но если еще и коструктор(ы) в защитный блок затащить, так еще и хинтов/варнингов от компилятора "слушать"...) Зачем?
И еще.... и даже с одним блоком финали мы не лишены возможности два раза освободить объект :)
← →
ZENsan © (2008-04-24 11:43) [47]Там обйектам нил присваивался перед блоком Трай.. Какие варнинги..
А если мы конструкторы в незащищённый блок поставим... то смотри:
Obj1 := TObj1.Create();{сработал, память выделилась}
Obj2 := TObj2.Create();{исключение}
try
...
finally
...
end;
Memory leak..
← →
{RASkov} © (2008-04-24 11:48) [48]> [47] ZENsan © (24.04.08 11:43)
> Там обйектам нил присваивался перед блоком Трай.. Какие варнинги..
Такой код появляется скорее из-за лени программиста нежели из-за профессианализма)
И для других может выглядеть запутанно :(
← →
ANB (2008-04-24 11:51) [49]
> Ega23 © (24.04.08 10:58) [39]
>
> > Затем, что ошибка может настичь и на Obj5 := TObj.Create;
>
> > где же тогда освобождать Obj1 … Obj5
>
>
> А в таком случае надо по-хорошему так:
>
> Obj1 := TObj.Create;
> try
> Obj2 := TObj.Create;
> try
> Obj3 := TObj.Create;
> try
> .......
> finally
> Obj3.Free;
> end;
> finally
> Obj2.Free;
> end;
> finally
> Obj1.Free;
> end;
> <Цитата>
Извращение и плохо читаемо.
← →
ZENsan © (2008-04-24 11:51) [50]Не факт. Смотри:
Obj1:=TObj.Create;
if Assigned(Obj1) then Obj1.Free;
if Assigned(Obj1) then Obj1.Free;
Ну а такой код-то от чего появился вдруг?
if Assigned(Obj1) then Obj1.Free;
if Assigned(Obj1) then Obj1.Free;
Конечно тут ошибка будет
← →
ZENsan © (2008-04-24 11:52) [51]Полностйу соглаес с АНБ
← →
ANB (2008-04-24 11:52) [52]
>
> {RASkov} © (24.04.08 11:39) [46]
> > [45] ZENsan © (24.04.08 11:34)
>
> А смысл? не вижу...(
> Но если еще и коструктор(ы) в защитный блок затащить, так
> еще и хинтов/варнингов от компилятора "слушать"...) Зачем?
>
> И еще.... и даже с одним блоком финали мы не лишены возможности
> два раза освободить объект :)
Ни хинтов не варнингов при таком способе нету.
← →
ANB (2008-04-24 11:53) [53]
> Arinyshka (24.04.08 11:28) [42]
> А мне велено почитать про секцию finalization. Может, так
> действительно проще?
> инициализировать и освободить в соотв секциях...
> Из советов мне понятен вариант с проверкой:
> if Assigned(Obj1) then> Obj1.Free;i
> тогда я никого не попытаюсь освободить дважды
Выделенное - совершенно лишний код. Фрее и так внутри проверяет, что ссылка на объект не равна NIL.
← →
ZENsan © (2008-04-24 11:55) [54]Мой способ вообще был нормальный:
Obj1 := nil;
Obj2 := nil;
try
Obj1 := TObj1.Create;
Obj2 := TObj2.Create;
...
finally
if Assigned(Obj1) then
FreeAndNil(Obj1);
if Assigned(Obj2) then
FreeAndNil(Obj2);
end;
← →
ЮЮ © (2008-04-24 11:55) [55]> Ну а такой код-то от чего появился вдруг?
Он появился от того, что появилась проверка if Assigned(Obj1) которая абсолютно ничего не дает.
Что с не, что без неё Obj1.Free сработает абсолютно одинаково.
← →
ZENsan © (2008-04-24 11:56) [56]Если исключение будет в сосздании второго объекта...????
Тогда ваша прого просто улетит...
← →
ZENsan © (2008-04-24 11:57) [57]"Не факт. Смотри:
Obj1:=TObj.Create;
if Assigned(Obj1) then Obj1.Free;
if Assigned(Obj1) then Obj1.Free;" - ето не мой код...
← →
ANB (2008-04-24 11:58) [58]
> ZENsan © (24.04.08 11:55) [54]
> Мой способ вообще был нормальный:
>
> Obj1 := nil;
> Obj2 := nil;
> try
> Obj1 := TObj1.Create;
> Obj2 := TObj2.Create;
> ...
> finally
> if Assigned(Obj1) then
> FreeAndNil(Obj1);
> if Assigned(Obj2) then
> FreeAndNil(Obj2);
> end;
А я не тебе и писал :).
Тем более твой код - почти такой же как и мой. Кистате, я года 3 назад так же писал, пока Саша Просторов не предложил мне взглянуть на реализацию Фрии :).
← →
ZENsan © (2008-04-24 11:59) [59]А я не тебе ;)
← →
ZENsan © (2008-04-24 12:01) [60]Ну ка ну ка чё там за фишка про Фрии..
Если вызывать Obj1.Free, когда Obj1 = nil или неинициализирован (локальная переменная в процедуре функции) - то будет исключение 100%...
← →
{RASkov} © (2008-04-24 12:03) [61]> [60] ZENsan © (24.04.08 12:01)
Проверь:var B: TObject;
begin
B:=nil;
B.Free;
end;
нет никаких АВ :)
← →
{RASkov} © (2008-04-24 12:09) [62]> [60] ZENsan © (24.04.08 12:01)
> nil или неинициализирован
Дело в том, что это разные вещи и приравнивание переменной Obj1 к nil - тажа самая инициализация по сути.
← →
ZENsan © (2008-04-24 12:10) [63]Согласен... Фрии - class procedure.
Но нил я присваиваю именно птоому что объекты когда они локальные в процедурах и функциях могут иметь рандом значения из стека. Поэтому без Obj1 := nil; лучше не жить...
А про фрии, никогда не знал - не полагался никогда на это. предпочитаю 7 раз отмерить - один раз отрезать.
← →
ZENsan © (2008-04-24 12:11) [64]Параметры функций/процедур не инициализируются автоматически в Делфи
← →
Плохиш © (2008-04-24 12:18) [65]
> ZENsan © (24.04.08 12:11) [64]
> Параметры функций/процедур не инициализируются автоматически
> в Делфи
Чем дальше в лес, тем толще партизаны...
PS. "Параметры функций/процедур" обычно передаются в эти функции/процедуры, если конечно для них не заданы значения по умолчанию.
PPS. А основы используемого языка программирования всё-таки почитай.
← →
ZENsan © (2008-04-24 12:19) [66]Спасибо за справочку {RASkov}, тоесть теперй код такой должен быть:
Obj1 := nil;
Obj2 := nil;
try
Obj1 := TObj1.Create;
Obj2 := TObj2.Create;
...
finally
FreeAndNil(Obj1);
FreeAndNil(Obj2);
end;
Ну ваще красота... но я всё же ставлю проверку (ну моразматик я, да :) )..
← →
{RASkov} © (2008-04-24 12:20) [67]> [63] ZENsan © (24.04.08 12:10)
> Согласен... Фрии - class procedure.
Во первых это статический приватный метод, не классовый.)
Во вторых
> предпочитаю 7 раз отмерить - один раз отрезать.
Тоже не есть верно. Зачем лишние расходы? Можно же еще и так делать и тоже будет верно:
if not Assigned(Ojb) and Obj=nil and (Not assigned(Obj) and Obj=nil) then Obj.Free;
:)
← →
ZENsan © (2008-04-24 12:21) [68]const
Obj: Tobj = nil;
ми про ето не говорим...
Поумничать - это хорошо конечно..
← →
ZENsan © (2008-04-24 12:22) [69]{RASkov} - :) это ты круто :)
← →
ZENsan © (2008-04-24 12:23) [70]"Во первых это статический приватный метод, не классовый.)" - в делфи это "class procedure/function". (wait)
← →
ЮЮ © (2008-04-24 12:26) [71]> [66] ZENsan © (24.04.08 12:19)
> finally
> FreeAndNil(Obj1);
> FreeAndNil(Obj2);
> end;
если Obj1 и Obj2 локальные, то нет смфсла в их обNilениее в finally, если «глобальные», т.е. поля объекта, то нет смысла в обNilениее до try.
← →
ZENsan © (2008-04-24 12:26) [72]Constructor i Destructor - единственные класс методы до реализации класс методов в делфи начиная по моему с 2005-ого..
← →
ZENsan © (2008-04-24 12:27) [73]Если поля обйекта то конечно. Я именно про случай если это локальные переменные не константы..
← →
ANB (2008-04-24 12:30) [74]
> то нет смфсла в их обNilениее в finally
Вобчем то да. Но могут быть разные глюки потом. Ну его нафиг - мне что жалко один раз выполнить короткое присваивание ? Тем более оно в функции живет.
← →
ЮЮ © (2008-04-24 12:32) [75]> Я именно про случай если это локальные переменные не константы…
зачем тогдаfinally
FreeAndNil(Obj1);
FreeAndNil(Obj2);
end;
так разве менее красиво
finally
Obj1.Free;
Obj2.Free;
end;
P.S. учитывая, что Obj2 := TObj2.Create; часто вызывает исключение, очень вероятно, что при удачном создании обоих объектов упадет с исключением Obj1.Free; и Obj2 останется неосвобожденным :)
← →
ЮЮ © (2008-04-24 12:36) [76]> [74] ANB (24.04.08 12:30)
> Вобчем то да. Но могут быть разные глюки потом
Глюки после смерти? Если они есть, значит проблемы в другом месте кода и это счастье, что тебе удалось уловить их хотя бы опосредованно.
← →
Восхищенный (2008-04-24 12:40) [77]> ZENsan © (24.04.08 12:26) [72]
> Constructor i Destructor - единственные класс методы до реализации класс
> методов в делфи начиная по моему с 2005-ого..
1. Конструктор и деструктор - вообще не классовые методы.
2. Классовые методы реализованы во всех версиях Delphi, начиная аж с 1.
3. В [65] Плохиш дал очень хороший совет. Конечно, можно и дальше переливать здесь из пустого в порожнее, но лучше все же последовать этому совету.
← →
{RASkov} © (2008-04-24 12:42) [78]> [70] ZENsan © (24.04.08 12:23)
TObject = class
constructor Create;
procedure Free;
class function InitInstance(Instance: Pointer): TObject;
procedure CleanupInstance;
function ClassType: TClass;
class function ClassName: ShortString;
class function ClassNameIs(const Name: string): Boolean;
......
Я конечно загнул с приватным :) но не классовый он....
← →
Kolan © (2008-04-24 12:46) [79]> но не классовый он…
Имхо, словоconstructor
подразумеваетclass function
, так что, имхо, классовый.
← →
{RASkov} © (2008-04-24 12:50) [80]> [79] Kolan © (24.04.08 12:46)
> так что, имхо, классовый.
Коструктор, да. Его нужно применять к классу, иначе(если к объекту: Obj.Create;) это не конструктор а вызов метода Create без распределения памяти....
Но я зря его(конструктор) подчеркнул, так как разговор был о Free)
Страницы: 1 2 3 4 5 6 7 8 9
10 11 12 13 14 15 16 17 вся ветка
Форум: "Начинающим";
Текущий архив: 2008.06.08;
Скачать: [xml.tar.bz2];
Память: 0.62 MB
Время: 0.105 c