Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2007.10.21;
Скачать: CL | DM;

Вниз

FreeAndNil   Найти похожие ветки 

 
mike_zav   (2007-09-21 17:37) [0]

В каких случаях применяют FreeAndNil? А в каких просто .Free?
Зачем это нужно? Если можно с примером.


 
Ega23 ©   (2007-09-21 17:40) [1]

FreeAndNil(obj) применяют в тех случаях, когда впадлу написать
obj.Free;
obj:=nil;


> Зачем это нужно?


Это нужно для того, чтобы в одном случае ссылка стала равной nil, а в другом - нет.

З.Ы. Ни разу FreeAndNil не использовал.


 
Инс ©   (2007-09-21 17:42) [2]


> В каких случаях применяют FreeAndNil?

Например, если в будущем понадобится проверить, уничтожен ли экземпляр, на который ссылается данная переменная/поле класса.


 
stanislav ©   (2007-09-21 17:45) [3]

http://delphimaster.net/view/2-1190379982/


 
Leonid Troyanovsky ©   (2007-09-21 17:48) [4]


> mike_zav   (21.09.07 17:37)  

> Зачем это нужно? Если можно с примером.

Да, собс-но, не нужно. Ну, может, писать короче.
Но, от неприятностей оно не спасет.

--
Regards, LVT.


 
Anatoly Podgoretsky ©   (2007-09-21 18:55) [5]

> mike_zav  (21.09.2007 17:37:00)  [0]

Никогда не применял, за ненадобностью подобной функций, которая была сделана Борландом для забывчивых и неумеющих. Наличие подобной функции как правило говорит о недостатках в программе.


 
Anatoly Podgoretsky ©   (2007-09-21 18:56) [6]

> Инс  (21.09.2007 17:42:02)  [2]

Переменная это недостаток, а поля можно и нужно делать контролируемыми.


 
mike_zav   (2007-09-21 19:34) [7]

Бррр.. так я и не понял одного, это должно спасти от ложного срабатывания Assign, при уже уничтоженном объекте?


 
Сергей М. ©   (2007-09-21 19:39) [8]


> mike_zav   (21.09.07 19:34) [7]



> это должно спасти .. ?


А куда ему деться с подводной лодки ?)

"Согласие есть продукт при полном непротивлении сторон" (С)

FreeAndNil "нилит" переменную, а Assigned, видя этот "нил", согласен и имеет все основания выдать False.


 
Инс ©   (2007-09-21 20:05) [9]


> Никогда не применял, за ненадобностью подобной функций,
> которая была сделана Борландом для забывчивых и неумеющих.
> Наличие подобной функции как правило говорит о недостатках
> в программе.

Ну, значит Borland сами забывчивы и неумеющие :) Например, в модуле Graphics - используется повсеместно. Например класс TBitmap метод GetCanvas вначале проверяет на равенство поля FCanvas nil, и только потом в случае успешной проверки создает экземпляр TCanvas. А когда Canvas становится невалидным (например, после вызова Dormant) - уничтожает ее и обнуляет ссылку. Теперь, если вдруг кто-либо обратится к свойству Canvas, снова вызывается GetCanvas, проверяется на nil и т.д.
Т.е. благодаря обнулению ссылок можно создавать вложенные объекты только по требованию.


 
Anatoly Podgoretsky ©   (2007-09-21 20:11) [10]

> Инс  (21.09.2007 20:05:09)  [9]

FCanvas это контролируемая вещь, которую не обойдешь, а обнулить я предпочту явно. Никто же не утверждает, что нельзя присваивать nil, только на пользовательском уровне, особенно для переменных это говорит о желании повторного использования переменной со всеми вытекающими от этого последствиями.


 
Инс ©   (2007-09-21 20:14) [11]


> [10] Anatoly Podgoretsky ©   (21.09.07 20:11)

Прошу прощения, не совсем понял вашу последнюю мысль...


 
Anatoly Podgoretsky ©   (2007-09-21 20:15) [12]

> Инс  (21.09.2007 20:14:11)  [11]

Что именно, я же много о чем говорил.
Может термин повторное использование переменных?


 
Инс ©   (2007-09-21 20:18) [13]


> FCanvas это контролируемая вещь, которую не обойдешь, а
> обнулить я предпочту явно.

Несколько раз перечитал это предложение, не могу понять смысл...


> Может термин повторное использование переменных?

Нет, с этим как раз все понятно.


 
Инс ©   (2007-09-21 20:21) [14]

А, все, кажется понял...


 
Anatoly Podgoretsky ©   (2007-09-21 20:21) [15]

> Инс  (21.09.2007 20:18:13)  [13]

> FCanvas это контролируемая вещь, которую не обойдешь, а
> обнулить я предпочту явно.

> Несколько раз перечитал это предложение, не могу понять смысл...

Все равно не понятно, что именно непонятно.
Что такое контролируемое или почему явно?


 
Anatoly Podgoretsky ©   (2007-09-21 20:23) [16]

Функция FreeAndNil сравни функии IncDay


 
Anatoly Podgoretsky ©   (2007-09-21 20:24) [17]

> Инс  (21.09.2007 20:21:14)  [14]

Не если не понял не стесняйся уточнить.


 
Инс ©   (2007-09-21 20:25) [18]

Комментирую [10]:


> только на пользовательском уровне

Ну, мы же вроде не только пользователи, но и программисты, иногда классы приходится писать самому. А следовательно может возникнуть подобная ситуация. И тогда можно действовать подобным образом. У меня даже когда-то было что-то похожее, но вот пока найти не могу, привел бы пример. А значит слишком категоричное утверждение о забывчивости и неумении становится не совсем верным. Случаи ведь разные бывают.


 
Anatoly Podgoretsky ©   (2007-09-21 20:35) [19]

У нас есть разделение, есть писатели компонент, а есть их пользователи и это даже может быть один и тот-же человек.
Утверждение не категоричное, а относится к культуре проектирования.
Надо предусмотреть меры по защите члена от непреднамеренного изменения за пределами класса, изоляция прямого доступа. Вот это и есть контролирование поведения на "системном" уровне.
Разница между


> public
>     X: type;


и

private
   FX: type;
published
   X: type read FX write FX;


большая и тем более для

private
   FX: type;
   function GetX: type;
   procedure SetX(X: type);
published
   X: type read FX write FX;


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

X := TBitmap.Create;
X := TBitmap.Create;
X := TBitmap.Create;
X := TBitmap.Create;
X := nil;


Никаких утечек, несмотря что нет разрушения старого значения.


 
Anatoly Podgoretsky ©   (2007-09-21 20:36) [20]

Очепятка в третьем примере

published
  X: type read GetX write SetX;


 
Инс ©   (2007-09-21 20:41) [21]


> Очепятка в третьем примере

Я догадался, все в порядке :)

Как считаете, в данной дискусии был раскрыт вопрос автора или нет? Истина найдена? Итоги подводить можно?


 
Anatoly Podgoretsky ©   (2007-09-21 20:44) [22]

> Инс  (21.09.2007 20:41:21)  [21]

Я думаю был раскрыт.
Функция была изобретена для ленивых и она не обязательна к использованию, более того она провоцирует на не совсем безопасный код.

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


 
Инс ©   (2007-09-21 20:52) [23]

Ясно, пациент безнадежен :) Ладно, дальше спорить не буду. Вот это разве что прокомментирую.

> Функция была изобретена для ленивых и она не обязательна к
> использованию, более того она провоцирует на не совсем безопасный код

Не обязательна. Можно написать в две строчки. А насчет провоцирует на небезопасный код - так любое техническое средство в руках дикаря - груда металлолома. Вы просто не хотите поверить в случай, что время жизни объекта, на который ссылается некий идентификатор, может подчиняться достаточно сложному закону (из-за оптимизации, например. Нужен - создаем, как только перестает быть нужен - уничтожаем), и тогда нет ничего проще, чем при уничтожении объекта всего лишь обнулить ссылку.


 
Anatoly Podgoretsky ©   (2007-09-21 21:03) [24]

> Инс  (21.09.2007 20:52:23)  [23]

Не будем рассматривать особые случае, я оперирую более общей сущностью.


 
Инс ©   (2007-09-21 21:09) [25]


> Не будем рассматривать особые случае, я оперирую более общей
> сущностью.

Я спорю только с категоричностью утверждения. Говорю, что в таком виде вывод не верный, есть оговорки. Вот и пытаюсь их обговорить...


 
Anatoly Podgoretsky ©   (2007-09-21 21:12) [26]

> Инс  (21.09.2007 21:09:25)  [25]

Вывод о категоричности неверный, это только кажется (стиль у меня такой). Я готов рассматривать и альтернативные варианты, вплоть до правомерности и ламерского кода.


 
Инс ©   (2007-09-21 23:10) [27]

И снова возвращаясь к первоначальной постановке вопроса... Мне тут статейку одну по этой теме подсказали (спасибо DRON ;-) ), немного трудновато написано, но все равно рекомендую:
http://blogs.codegear.com/abauer/2006/11/01/28852


 
Anatoly Podgoretsky ©   (2007-09-22 11:56) [28]

> Инс  (21.09.2007 23:10:27)  [27]

Полемика NilAndFree или FreeAndNil ведется с момента появления функции.
Так же как и необходимость в данной функции.
Все остаются при своих.


 
oxffff ©   (2007-09-22 13:22) [29]


> Anatoly Podgoretsky ©   (22.09.07 11:56) [28]
> > Инс  (21.09.2007 23:10:27)  [27]
>
> Полемика NilAndFree или FreeAndNil ведется с момента появления
> функции.
> Так же как и необходимость в данной функции.
> Все остаются при своих.


А спор о чем?


 
Anatoly Podgoretsky ©   (2007-09-22 13:31) [30]

> oxffff  (22.09.2007 13:22:29)  [29]

Спор ведется о буквах, мол неправильное название и спор ведется уже не один год.


 
oxffff ©   (2007-09-22 13:34) [31]


> Anatoly Podgoretsky ©   (22.09.07 13:31) [30]
> > oxffff  (22.09.2007 13:22:29)  [29]
>
> Спор ведется о буквах, мол неправильное название и спор
> ведется уже не один год.


Дык и текущая реализация не идеальна.

Ловим AV.
:)

procedure TForm1.Button1Click(Sender: TObject);
var a:^TObject;
begin
a:=nil;
Freeandnil(a^);
end;


 
Anatoly Podgoretsky ©   (2007-09-22 13:44) [32]

> oxffff  (22.09.2007 13:34:31)  [31]

Реализаций по сути две
FreeAndNil и NilAndFree

Реализация функции мне не нравится по следующей причине

procedure FreeAndNil(var Obj);

Видим уход от типизации и соответсвенно невозможность проверить еще на этапе компиляции.
Почему они так поступили конечно понятно, но я бы их расстрелял.
Вот если бы они реализовали так

procedure FreeAndNil(var Obj: TObject);

То таких бы претензий у меня не было. Компилятор бы просто не пропустил многие ошибки.


 
Anatoly Podgoretsky ©   (2007-09-22 13:46) [33]

Кстати с Free такой проблемы просто нет, там все в рамках идеологии Паскаля и реализация правильная.
Историю как появилась данная и другие подобные функции я помню, как все развивалось в Борланде в сторону попсовости, в сторону популизма.


 
oxffff ©   (2007-09-22 13:51) [34]


> Anatoly Podgoretsky ©   (22.09.07 13:44) [32]
> > oxffff  (22.09.2007 13:34:31)  [31]
>
> Реализаций по сути две
> FreeAndNil и NilAndFree
>
> Реализация функции мне не нравится по следующей причине
>
> procedure FreeAndNil(var Obj);
>
> Видим уход от типизации и соответсвенно невозможность проверить
> еще на этапе компиляции.
> Почему они так поступили конечно понятно, но я бы их расстрелял.
>
> Вот если бы они реализовали так
>
> procedure FreeAndNil(var Obj: TObject);
>
> То таких бы претензий у меня не было. Компилятор бы просто
> не пропустил многие ошибки.


А мне собственно не понятно почему они поставили untyped параметр?


 
Anatoly Podgoretsky ©   (2007-09-22 13:58) [35]

> oxffff  (22.09.2007 13:51:34)  [34]

> А мне собственно не понятно почему они поставили untyped параметр?

Посмотри исходные коды, может станет понятно.
Но с тезисом, что это бардак и некомпетентность ты в принципе согласен?


 
oxffff ©   (2007-09-22 14:16) [36]


> Anatoly Podgoretsky ©   (22.09.07 13:58) [35]
> > oxffff  (22.09.2007 13:51:34)  [34]
>
> > А мне собственно не понятно почему они поставили untyped
> параметр?
>
> Посмотри исходные коды, может станет понятно.
> Но с тезисом, что это бардак и некомпетентность ты в принципе
> согласен?


С тезисом я согласен.
Действительно FreeAndNil(var Obj: TObject) более строгое определение.

Понял ваш намек. Чтобы не мучиться с приведение var параметров.

Тогда. Вопрос.

Почему бы не добавить поддержку неявного приведения var параметров.

Если Tobject и pointer "совместимы"
Если потомок и родитель "совместимы"

Почему тогда  ссылка(var параметр) на эти типы не совместимы.

Например мы же можем спокойно присваивать потомков Tobject к pointer и наоборот. Почему не сделать такое неявное приведение для var параметров.
Сейчас в голову не приходит каких либо проблем с этим. IMHO.


 
oxffff ©   (2007-09-22 14:21) [37]

Почему выходит
Types of actual and formal var parameters must be identical?

Для

procedure abc(var a:Tobject);
begin
end;

procedure TForm1.Button1Click(Sender: TObject);
var a:tControl;
begin
abc(a);
end;

К каким проблемам это может привести?


 
Anatoly Podgoretsky ©   (2007-09-22 14:27) [38]

> oxffff  (22.09.2007 14:21:37)  [37]

В данном случае ни к каким, поскольку tControl наследник от Tobject и обладает всеми его методами и полями. Вот наоборот нельзя.


 
oxffff ©   (2007-09-22 14:32) [39]


> Anatoly Podgoretsky ©   (22.09.07 14:27) [38]
> > oxffff  (22.09.2007 14:21:37)  [37]
>
> В данном случае ни к каким, поскольку tControl наследник
> от Tobject и обладает всеми его методами и полями. Вот наоборот
> нельзя.


И я о том же. Только почему компилятор не пропускает это?

В чем причина этого ограничения.

Пойдем дальше. Почему ругается?

procedure abc(var a:Tobject);
begin
end;

procedure TForm1.Button1Click(Sender: TObject);
var a:pointer;
begin
abc(a);
end;

Tobject и pointer "совместимы". А передача как var параметра накладывает самые строгие ограничения.

Не считаете ли вы это упущением?


 
Anatoly Podgoretsky ©   (2007-09-22 14:36) [40]

> oxffff  (22.09.2007 14:32:39)  [39]

Может из-за var
В этом случае да, параметры не идентичны.


 
oxffff ©   (2007-09-22 14:44) [41]


> Anatoly Podgoretsky ©   (22.09.07 14:36) [40]
> > oxffff  (22.09.2007 14:32:39)  [39]
>
> Может из-за var
> В этом случае да, параметры не идентичны.


Так является ли это упущением с вашей точки зрения?

Ведь именно по этой причине FreeAndNil имеет вид

procedure FreeAndNil(var Obj);

а не

procedure FreeAndNil(var Obj:Tobject);

Почему если типы совместимы, ссылки на них не совместимы?

Повторю еще раз

Так является ли это упущением с вашей точки зрения?


 
Anatoly Podgoretsky ©   (2007-09-22 14:50) [42]

> oxffff  (22.09.2007 14:44:41)  [41]

Мне как то все равно до FreeAndNil я ее не использую.


 
oxffff ©   (2007-09-22 14:54) [43]

Еще из этого разряда. Почему компилятор не пропускает

procedure abc(p:ppointer);
begin
end;

procedure TForm1.Button1Click(Sender: TObject);
var a:^Tobject;
begin
abc(a);
end;

Incompatible types: "TObject" and "Pointer"

IMHO.
Компилятор слегка подстроить для нормальной обработки этой ситуации.
А именно, если типы совместимы, то и ссылки и указатели на них должны совместимы
IMHO.


 
Anatoly Podgoretsky ©   (2007-09-22 14:57) [44]

> oxffff  (22.09.2007 14:54:43)  [43]

Ну так и говорит - типы не совместимые.


 
oxffff ©   (2007-09-22 15:00) [45]


> Anatoly Podgoretsky ©   (22.09.07 14:57) [44]
> > oxffff  (22.09.2007 14:54:43)  [43]
>
> Ну так и говорит - типы не совместимые.


Ну а почему вы можете присвоить Tobject к pointer. И наоборот.

Почему?


 
Leonid Troyanovsky ©   (2007-09-22 15:00) [46]


> oxffff ©   (22.09.07 14:54) [43]

> Еще из этого разряда. Почему компилятор не пропускает

Конечно, достаточно уйти от var и никаких ограничений,
за исключением необходимости добавлять @.

type
 PObject = ^TObject;
 TMyObject = class
   x: TObject;
 end;

procedure abc(a: PObject);
begin
 ShowMessage(a^.ClassName);
 a^ := nil;
end;

procedure TForm1.Button1Click(Sender: TObject);
var a:tMyobject;
begin
a:= TMyobject.Create;
a.x := TObject.Create;
abc(@a.x);
Caption :=  Format("%p", [Pointer(a.x)]);
end;


Только, подобная "гибкость" только плодит проблемы.

--
Regards, LVT.


 
oxffff ©   (2007-09-22 15:02) [47]

Если следовать логике компилятора.

Он должен не пропустить. Однако вы знаете он пропустит.

procedure abc(p:pointer);
begin
end;

procedure TForm1.Button1Click(Sender: TObject);
var a:Tobject;
begin
abc(a);
end;


 
oxffff ©   (2007-09-22 15:07) [48]


> Только, подобная "гибкость" только плодит проблемы.


В чем проблема в вашем примере?


 
Leonid Troyanovsky ©   (2007-09-22 15:13) [49]


> oxffff ©   (22.09.07 15:02) [47]

> Он должен не пропустить. Однако вы знаете он пропустит.

Ограничение относится только к var параметрам,
Types of actual and formal var parameters must be identical (E2033)

For a variable parameter, the actual argument must be of the exact type of the formal parameter.

Почитай статью.

Не пойму в чем смущение ума :)

--
Regards, LVT.


 
Leonid Troyanovsky ©   (2007-09-22 15:16) [50]


> oxffff ©   (22.09.07 15:07) [48]

> В чем проблема в вашем примере?

В моем их нет, но в подобных - отсутствие возможности контролировать типы, т.е. та самая совместимость TObject - pointer.

--
Regards, LVT.


 
oxffff ©   (2007-09-22 15:19) [51]


> Types of actual and formal var parameters must be identical
> (E2033)



> exact type


Да но к каким потенциальным граблям могут, если мы попросим их расширить эту функциональность. Вопрос в этом.

Вернемся к простому примеру с Tconrol и Tobject.

procedure abc(var a:Tobject);
begin
end;

procedure TForm1.Button1Click(Sender: TObject);
var a:tControl;
begin
abc(a);
end;

Почему бы не пропускать данный вызов. Ведь Tobject является подмножеством tControl и поэтому совместим.

Почему авторы ограничили именно до  exact type?


 
oxffff ©   (2007-09-22 15:22) [52]


> Leonid Troyanovsky ©   (22.09.07 15:16) [50]
>
> > oxffff ©   (22.09.07 15:07) [48]
>
> > В чем проблема в вашем примере?
>
> В моем их нет, но в подобных - отсутствие возможности контролировать
> типы, т.е. та самая совместимость TObject - pointer.


Но тем не менее проблем будет имхо не больше, чем когда вы пишите так

procedure TForm1.Button1Click(Sender: TObject);
var a:pointer;
begin
a:=self;
end;


 
Ping   (2007-09-22 15:28) [53]

Почему бы не пропускать данный вызов. Ведь Tobject является подмножеством tControl и поэтому совместим.

procedure Test(var Obj: TObject);
begin
 Obj := TBitmap.Create;
end;

procedure TForm1.Button1Click(Sender: TObject);
var
 Obj: TWinControl;
begin
 Test(Obj);
end;


Вот поэтому...


 
oxffff ©   (2007-09-22 15:34) [54]


> Вот поэтому...


Но Imho это решаемо.
Захочешь ограничить. Сделаешь так

procedure Test(var Obj: TControl);
begin
Obj := TBitmap.Create;
end;


 
Ping   (2007-09-22 15:37) [55]

Захочешь ограничить. Сделаешь так

Как это относится к FreeAndNil()?


 
oxffff ©   (2007-09-22 15:41) [56]


> Как это относится к FreeAndNil()?


oxffff ©   (22.09.07 14:44) [41]


 
Leonid Troyanovsky ©   (2007-09-22 15:46) [57]


> oxffff ©   (22.09.07 15:22) [52]

> Но тем не менее проблем будет имхо не больше, чем когда
> вы пишите так

Ну, это, скорее, вынужденые локальные меры.
Информация о типе, видимо, сохраняется "в уме" пишущего.
А от глобальных процедур требуют большего.
Т.е., чтобы случайно не передать туда не то.

--
Regards, LVT.


 
Ping   (2007-09-22 15:52) [58]

В частном случае, для FreeAndNil(), когда производится только обниление переменной - такое решение, возможно, и подошло бы.

Но

При передаче параметров по ссылке (var), при предлагаемом тобой подходе, можно вернуть все, что душе угодно (в пределах наследования). Компилятор  - он не телепат. Есть формальная логика. И если для Паскаля постулируется сильная типизация, то компилятор, при передаче по ссылке, будет требовать, чтобы передаваемая ссылка была на объект требуемого типа. Не нравится - пиши на С.

P.S. "Я дерусь... потому что я... дерусь!" (С) ?


 
oxffff ©   (2007-09-22 15:59) [59]


>  И если для Паскаля постулируется сильная типизация, то
> компилятор, при передаче по ссылке, будет требовать, чтобы
> передаваемая ссылка была на объект требуемого типа.


Сильная типизация?
А как насчет в совместимости pointer и Tobject?
Далее как насчет дочерних типов?

>P.S. "Я дерусь... потому что я... дерусь!" (С) ?

Я хочу сделать свою жизнь проще. :)


 
Anatoly Podgoretsky ©   (2007-09-22 16:18) [60]

> oxffff  (22.09.2007 15:59:59)  [59]

Pointer и pPointer разные вещи, вторая уже строгая типизация


 
oxffff ©   (2007-09-22 16:29) [61]


> Anatoly Podgoretsky ©   (22.09.07 16:18) [60]
> > oxffff  (22.09.2007 15:59:59)  [59]
>
> Pointer и pPointer разные вещи, вторая уже строгая типизация


А почему язык со строгой типазацией закрывает глаза на первую?
И причину такого поведения не подскажите?

Почему бы не сделать свой выбор в пользу неявного приведения для ссылочных типов с простой семантикой копирования.
А именно для типов Tobject, нетипизированного указателя и указателей на типы с простой семантикой копирования? А как же для ссылок на эти типы.


 
Anatoly Podgoretsky ©   (2007-09-22 16:34) [62]

То что это документировано, или передаешь var Name без типа или var Name: тип, тогда должно быть соответствие формальных и фактических параметров.


 
Anatoly Podgoretsky ©   (2007-09-22 16:35) [63]

А насчет хотелок, многие хотели бы превратить Паскаль в Си или Бейсик и обидно, что Борланд иногда идет на поводу.


 
oxffff ©   (2007-09-22 16:39) [64]


> Anatoly Podgoretsky ©   (22.09.07 16:34) [62]
> То что это документировано, или передаешь var Name без типа
> или var Name: тип, тогда должно быть соответствие формальных
> и фактических параметров.


Да об этом и речи нет.

Я о расширении языка.
И чтобы не было каламбура по типу oxffff ©   (22.09.07 14:54) [43].

Только скажите как в языке со строгой типизацией присутствуют конструкции untyped var, out, const педачи параметров?


 
Anatoly Podgoretsky ©   (2007-09-22 16:41) [65]

> oxffff  (22.09.2007 16:39:04)  [64]

К Вирту, он папа и к извращенцам из Борланда.


 
oxffff ©   (2007-09-22 16:45) [66]


> Anatoly Podgoretsky ©   (22.09.07 16:35) [63]
> А насчет хотелок, многие хотели бы превратить Паскаль в
> Си или Бейсик и обидно, что Борланд иногда идет на поводу.
>


Я все таки думую нужно быть не гордым, а расчетливым и "видеть" как одни конструкции удобнее, или быстрее других. Согласитесь, что конструкция for in действительна удобна. Хоть я и пишу до сих пор на 7 версии.Но считаю ее удобной. Также как и внесение статических методов в record.
Также как и nested types, class var. И даже те же Class helpers и record helper.
Не смотря на что приходится писать и на других языках включая С++,C#, ASM и ряд других.
Все равно Delphi мне ближе.


 
oxffff ©   (2007-09-22 16:50) [67]


> Но считаю ее удобной.


Я о новых конструкциях.

Сейчас я поехал в баню париться. :)
Вечером приеду и с вашего позволения я был бы рад продолжить дисскусию.
Спасибо всем за диалог.


 
Leonid Troyanovsky ©   (2007-09-22 16:55) [68]


> oxffff ©   (22.09.07 16:29) [61]

> Почему бы не сделать свой выбор в пользу неявного приведения
> для ссылочных типов с простой семантикой копирования.
> А именно для типов Tobject, нетипизированного указателя
> и указателей на типы с простой семантикой копирования? А
> как же для ссылок на эти типы.

А зачем?
Передача var TObject - извращение, FreeAndNil тому иллюстрация.

Все, что нужно потомку TObject должно быть в _его_ методах,
а не в глобальных регулярных процедурах.

--
Regards, LVT.


 
oxffff ©   (2007-09-24 10:09) [69]


> Все, что нужно потомку TObject должно быть в _его_ методах,
>
> а не в глобальных регулярных процедурах.


Согласитесь, что переменная типа  Tobject является лишь ссылкой на объект. А методы "должны" выполнять операции связанные с объектом, а не со ссылкой на него. Поэтому технически невозможно "грамотно" обнулить ссылку на объект, по причине того, что self передается by value.
А передовать ссылку на объект by ref в метод объекта не "грамотно".
Конечно можно создать невиртуальный классовый метод в Tobject, который принимает ссылку на объект и делает то, что делает FreeAndNil.
Но фактически классовый метод является регулярной функцией с ограниченным scope и дополнительным параметром на VMT, что избыточно по причине того, что VMT является ненужным параметром, и его мы может при желании изъвлечь из объекта.

Таким образом из-за ref семантики объектов в delphi операции над ссылкой и вынесли за пределы object scope. Поэтому это не извращение.

Вопрос, а как вы бы постулили в C++, где object is value type semantic?


 
Kolan ©   (2007-09-24 10:11) [70]

> конструкция for in действительна удобна. Хоть я и пишу до
> сих пор на 7 версии.Но считаю ее удобной.

Вот потому и считаешь, а я получал internal error из-за неё. Поэтому не использую&#133


 
oxffff ©   (2007-09-24 10:20) [71]


> Kolan ©   (24.09.07 10:11) [70]
> > конструкция for in действительна удобна. Хоть я и пишу
> до
> > сих пор на 7 версии.Но считаю ее удобной.
>
> Вот потому и считаешь, а я получал internal error из-за
> неё. Поэтому не использую…


oxffff ©   (22.09.07 16:50) [67]

Более того я выявил баг в реализации for in и отправил на qc, который получил уже open статус

Но тем не менее cчитаю ее удобной.


 
Kolan ©   (2007-09-24 10:30) [72]

> Но тем не менее cчитаю ее удобной.

Если бы переменную не заводить, то былобы хорошо совсем&#133


 
Turbouser ©   (2007-09-24 10:40) [73]

> [16] Anatoly Podgoretsky ©   (21.09.07 20:23)

Посмеялся :)) Спасибо за порцию позитива :)))


 
Leonid Troyanovsky ©   (2007-09-24 11:29) [74]


> oxffff ©   (24.09.07 10:09) [69]

> Согласитесь, что переменная типа  Tobject является лишь
> ссылкой на объект. А методы "должны" выполнять операции
> связанные с объектом, а не со ссылкой на него. Поэтому технически
> невозможно "грамотно" обнулить ссылку на объект, по причине
> того, что self передается by value.

Ссылка на объект отличается от самого объекта (тоже ссылки)
лишь (лишним) разыменованием. By-reference vs by-value - тоже.

Ну, а раз оно лишнее, то это и есть изврат :)

Да и, во-ще, тема, IMHO, себя исчерпала,
а FreeAndNil - MD.

--
Regards, LVT.


 
Плохиш ©   (2007-09-24 11:53) [75]

"Каждому овощу своё время"...


 
oxffff ©   (2007-09-24 11:55) [76]


> Leonid Troyanovsky ©   (24.09.07 11:29) [74]
>
> > oxffff ©   (24.09.07 10:09) [69]
>
> > Согласитесь, что переменная типа  Tobject является лишь
>
> > ссылкой на объект. А методы "должны" выполнять операции
>
> > связанные с объектом, а не со ссылкой на него. Поэтому
> технически
> > невозможно "грамотно" обнулить ссылку на объект, по причине
>
> > того, что self передается by value.
>
> Ссылка на объект отличается от самого объекта (тоже ссылки)
> лишь (лишним) разыменованием. By-reference vs by-value -
>  тоже.
>
> Ну, а раз оно лишнее, то это и есть изврат :)
>
> Да и, во-ще, тема, IMHO, себя исчерпала,
> а FreeAndNil - MD.
>
> --
> Regards, LVT.


Я думаю мы с вами говорим о разных вещах.


 
oxffff ©   (2007-09-24 12:12) [77]


> Ссылка на объект отличается от самого объекта (тоже ссылки)
> лишь (лишним) разыменованием. By-reference vs by-value -
>  тоже.


Методы связаны с блоком памяти в куче, а не с самой ссылкой на этот блок.
Поэтому обнуление ссылки является грамотным вынесением в регулярную процедуру.

А вы как предлагаете?

procedure Tobject.FreeAndNil(var obj:Tobject);?
или class procedure Tobject.FreeAndNil(var obj:Tobject); ?


 
Anatoly Podgoretsky ©   (2007-09-24 12:26) [78]

> oxffff  (24.09.2007 12:12:17)  [77]

Tobject.Free;
Tobject := nil;

И не будет таких фокусов, как

FreeAndNil(Integer)


 
oxffff ©   (2007-09-24 12:59) [79]


> FreeAndNil(Integer)


freeandnil(integer);
freeandnil(5);

Такое даже не откомпилируется. ;)

Тогда уж типизировать параметр.


 
Игорь Шевченко ©   (2007-09-24 13:04) [80]

Borland же честно подписал "Be careful to only pass TObjects to this routine." :)


 
Anatoly Podgoretsky ©   (2007-09-24 13:04) [81]

Откомпилируется, не в таком конец виде, это же шаблон

var
  I: Integer;
begin
  I := 0;
  FreeAndNil(I);


 
Anatoly Podgoretsky ©   (2007-09-24 13:14) [82]

> Игорь Шевченко  (24.09.2007 13:04:20)  [80]

В гробу такую честность.


 
Инс ©   (2007-09-24 13:24) [83]


> Функция FreeAndNil сравни функии IncDay

IncDay - хорошая функция. Позволяет не привязываться к реализации типа TDateTime, а заодно делает код более читаемым, особенно если в нем интенсивно используются подобные IncXXX-функции.


 
Turbouser ©   (2007-09-24 13:30) [84]

> [83] Инс ©   (24.09.07 13:24)
> IncDay — хорошая функция.

=))) Был тут энтузиаст :)
Свой  incday изобрел — у EGA23 до сих пор наверное
на стене висит — бо настроение поднимать :)))


 
Leonid Troyanovsky ©   (2007-09-24 13:32) [85]


> oxffff ©   (24.09.07 12:12) [77]

Согласен с Анатолием.

Хорошо б еще не забывать,
что ссылка может быть не единственной.

--
Regards, LVT.


 
Anatoly Podgoretsky ©   (2007-09-24 13:56) [86]

> Leonid Troyanovsky  (24.09.2007 13:32:25)  [85]

Правильно не надо закладываться на повторное использование переменных.
Просто надо решать надо иначе, через защищенное поле и контролируемое свойство и волосы будут шелковистыми.
Это решение дешевле, чем искать проблемы, героически с ними бороться.
А основная претензия к функции, что параметр не типизированый, со всем вытекающим из этого.


 
oxffff ©   (2007-09-24 14:41) [87]


> А основная претензия к функции, что параметр не типизированый,
>  со всем вытекающим из этого.


Так сделали они это по известным причинам, на которые вы намекали выше.
А именно, чтобы использовать в качестве параметра, любой ссылочный тип в основном Tobject и pointer. Но поскольку они не совместимы, если их передавать как var.

Им достаточно было сделать то, что я предлагаю, а именно сделать неявное приведение для ccылочных типов с простой семантикой копирования переданных как var параметр. И было бы счастье и удобство.


 
Инс ©   (2007-09-24 14:46) [88]


> Anatoly Podgoretsky ©   (24.09.07 13:04) [81]

Что, неужели вы в своих проектах так и делали?


 
Anatoly Podgoretsky ©   (2007-09-24 14:58) [89]

> oxffff  (24.09.2007 14:41:27)  [87]

Ну причины мы разобрали, а вот претензии остались.
Правда никто и не заставляет это использовать.
Счастье то будет в количестве строк и дополнительном геморое. Вот если они сделают это на уровне языка, тогда другое дело, только нафиг оно нужно. Пусть программист несет ответственность за свои действия.


 
Anatoly Podgoretsky ©   (2007-09-24 15:00) [90]


> Что, неужели вы в своих проектах так и делали?

Конечно нет, это же демонстрация. Да и как бы я мог это сделать, если я не использую FreeAndNil


 
Leonid Troyanovsky ©   (2007-09-24 15:02) [91]


> Anatoly Podgoretsky ©   (24.09.07 13:56) [86]

> Просто надо решать надо иначе, через защищенное поле и контролируемое
> свойство

Я даже предлагал как-то пример подобного

http://groups.google.com/group/fido7.ru.delphi.chainik/msg/2af895b1f348cbd1?dmode=source&output=gplain

--
Regards, LVT.


 
oxffff ©   (2007-09-24 15:03) [92]


> Вот если они сделают это на уровне языка, тогда другое дело,
>  только нафиг оно нужно


Так я именно об этом. :)


 
Инс ©   (2007-09-24 15:06) [93]


> Конечно нет, это же демонстрация. Да и как бы я мог это
> сделать, если я не использую FreeAndNil

Насколько я понял, вы не используете именно потому, что боитесь так сделать. Странная у вас позиция, ну не нравится вам, и не пользуйтесь. Какой тут геморой может быть, кроме того надуманного, что вы привели, я не знаю. Раз уж такое дело, то и Dispose использовать вредно. Там ведь параметр типа Pointer стоит, который на самом деле таковым быть не должен.


 
Anatoly Podgoretsky ©   (2007-09-24 15:08) [94]

> Leonid Troyanovsky  (24.09.2007 15:02:31)  [91]

Так это решение вполне квалифицированое, в рамках идеологии ООП Дельфи.


 
Anatoly Podgoretsky ©   (2007-09-24 15:09) [95]

> oxffff  (24.09.2007 15:03:32)  [92]

Ты об нафиг оно нужно


 
Anatoly Podgoretsky ©   (2007-09-24 15:16) [96]

> Инс  (24.09.2007 15:06:33)  [93]

Не боюсь, я уже давно ничего не боюсь. Выбор сделан с осознанием.
Таки и не использую.
А кто сказал, что я Dispose использую?


 
oxffff ©   (2007-09-24 15:17) [97]


> Anatoly Podgoretsky ©   (24.09.07 15:09) [95]
> > oxffff  (24.09.2007 15:03:32)  [92]
>
> Ты об нафиг оно нужно


:)

Вот если они сделают это на уровне языка


 
Инс ©   (2007-09-24 15:22) [98]


> А кто сказал, что я Dispose использую?

А где, говоря о Dispose, я сказал "Вы"?


 
Anatoly Podgoretsky ©   (2007-09-24 15:23) [99]

В контексте сообщения отнес к себе, а оказалось я тут не причем.


 
Инс ©   (2007-09-24 15:30) [100]

А интерфейсами лучше вообще никогда не пользоваться, там в одном из ключевых методов (QueryInterface) вообще out-параметр.


 
Плохиш ©   (2007-09-24 15:31) [101]


> Раз уж такое дело, то и Dispose использовать вредно.

Борланды в справке всё подробненько расписали, но "не царское это дело читать справку" у ССЗБ-н...


 
Инс ©   (2007-09-24 15:32) [102]


> Борланды в справке всё подробненько расписали, но "не царское
> это дело читать справку" у ССЗБ-н...

Это ты не мне, а [82] объясни.


 
Anatoly Podgoretsky ©   (2007-09-24 15:38) [103]

Чего тут спорить, с момента появления FreeAndNil ломают копья.
Разве это недостаточный критерий порочности?


 
Инс ©   (2007-09-24 15:41) [104]


> Чего тут спорить, с момента появления FreeAndNil ломают
> копья.

А до этого не ломали? Примеры поломаных об FreeAndNil копий в студию. Только не нужно приводить примеры, когда пострадавшие - уже упомянутые выше ССЗБ, они и на ровном месте себе шею сломают.


 
Джо ©   (2007-09-24 15:51) [105]

> [93] Инс ©   (24.09.07 15:06)
> Раз уж такое дело, то и Dispose использовать вредно. Там ведь  
> параметр типа Pointer стоит, который на самом деле таковым быть не
> должен.

Как это «не должен» и почему так?


 
Anatoly Podgoretsky ©   (2007-09-24 15:56) [106]

> Инс  (24.09.2007 15:41:44)  [104]

> Примеры поломаных об FreeAndNil копий в студию.

Так выброшены, и копья ломают не из-за пострадавших, они действительно ССЗБ
Ломают над нужностью/не нужностью, из-за названия, из-за политики Борланда, которые во многих случаях пошли по популисткому пути, после Д5.
Я на стороне тех, кто не согласен с Борландом.


 
Anatoly Podgoretsky ©   (2007-09-24 15:59) [107]

> Джо  (24.09.2007 15:51:45)  [105]

Не знаю, давно не использовал Dispose, но по моему должен, это же указатель на структуру или простой тип, а тут речь об объектах.
Разные все таки вещи. Я всегда использую GetMem/FreeMem может крома младенческих лет. Эти функции честные - сказано выделить память и никаких других толкований.


 
Инс ©   (2007-09-24 15:59) [108]


> Джо ©   (24.09.07 15:51) [105]

Мда...

type
 PMyRec = ^TMyRec;
 TMyRec = record
   s: String;
   i: Integer;
 end;

....

var
 rec: PMyRec;
 p: Pointer;
begin
 New(rec);
 rec^.s:="123";
 p:=rec;
 Dispose(p);
end;

Ловим утечку памяти из-за того, что память под строку освобождена не будет. А если сделать Dispose(rec) - все будет нормально.


 
Инс ©   (2007-09-24 16:04) [109]

GetMem/FreeMem - это тупое выделение и освобождение памяти. New и Dispose - умнее, они инициализируют и финализируют поля финализируемых типов. Если вызвать Dispose и передать ей нетипизированный указатель на стуктуру, содержащую такие поля, они финализированы не будут. Это очень частая ошибка.


 
oxffff ©   (2007-09-24 16:16) [110]


> Инс ©   (24.09.07 16:04) [109]
> GetMem/FreeMem - это тупое выделение и освобождение памяти.
>  New и Dispose - умнее, они инициализируют и финализируют
> поля финализируемых типов. Если вызвать Dispose и передать
> ей нетипизированный указатель на стуктуру, содержащую такие
> поля, они финализированы не будут. Это очень частая ошибка.
>


Тебе же сказали, что все делают ручками.

FreeMem(pointer(integer(rec^.s)-8))

Typeinfo это вред.

:)


 
oxffff ©   (2007-09-24 16:26) [111]


> Тебе же сказали, что все делают ручками.


А при возможности вообще пишут не на ассемблере, а сразу в машинных кодах.


 
Anatoly Podgoretsky ©   (2007-09-24 16:35) [112]

> Инс  (24.09.2007 16:04:49)  [109]

Я хорошо знаю, что они умнее и для чего нужны, но что же мне делать, если я не использую таких структур, да и память уже не помню когда выделял.


 
Anatoly Podgoretsky ©   (2007-09-24 16:36) [113]

> oxffff  (24.09.2007 16:26:51)  [111]

Не в ту степь обсуждение пошло, давайте продолжать обсасывать, облизывать FreeAndNil или исписались?


 
oxffff ©   (2007-09-24 16:38) [114]


> Anatoly Podgoretsky ©   (24.09.07 16:36) [113]
> > oxffff  (24.09.2007 16:26:51)  [111]
>
> Не в ту степь обсуждение пошло, давайте продолжать обсасывать,
>  облизывать FreeAndNil или исписались?


oxffff ©   (24.09.07 15:17) [97]


 
Инс ©   (2007-09-24 16:44) [115]


> Я хорошо знаю, что они умнее и для чего нужны, но что же
> мне делать, если я не использую таких структур, да и память
> уже не помню когда выделял.

Это я г-ну Джо объяснял, почему в парметрах к процедуре Dispose должен быть не Pointer, а типизированный указатель, хотя и вам тоже полезно будет, так как то, что вы хорошо знаете, что они умнее и для чего нужны - я уже сомневаюсь, судя по фразе "Не знаю, давно не использовал Dispose, но по моему должен". А насчет FreeAndNil - что тут обсуждать. Все уже давно сказано, каждый остается при своем. Я вот только понять не могу, почему те, кто не согласен с Borland, до сих пор сидят за Delphi...


 
Anatoly Podgoretsky ©   (2007-09-24 16:51) [116]

> Инс  (24.09.2007 16:44:55)  [115]

Это я сейчас не знаю (не помню), но это не относится к тому моменту, когда я захочу использовать.


 
Джо ©   (2007-09-24 17:12) [117]

> [115] Инс ©   (24.09.07 16:44)
> Это я г-ну Джо объяснял, почему в парметрах к процедуре
> Dispose должен быть не Pointer, а типизированный указатель

Увы, синтаксис не позволяет.


 
Инс ©   (2007-09-24 17:19) [118]


> Увы, синтаксис не позволяет.

Так и с FreeAndNil та же история. Нельзя написать
procedure FreeAndNil(var Obj: TObject);


 
Leonid Troyanovsky ©   (2007-09-24 17:35) [119]


> Джо ©   (24.09.07 17:12) [117]

> > Dispose должен быть не Pointer, а типизированный указатель
>
> Увы, синтаксис не позволяет.

А почему "увы"? По-моему, да и хрен с ним.
Кому сейчас нужны структуры со стрингами и вариантами.
Т.е., кому нужны - пользуют объекты.

--
Regards, LVT.


 
Джо ©   (2007-09-24 20:11) [120]

> [118] Инс ©   (24.09.07 17:19)
> Так и с FreeAndNil та же история. Нельзя написать
> procedure FreeAndNil(var Obj: TObject);

Да сколько угодно :)


> [119] Leonid Troyanovsky ©   (24.09.07 17:35)
>
> > Джо ©   (24.09.07 17:12) [117]
>
> > > Dispose должен быть не Pointer, а типизированный указатель
> >
> > Увы, синтаксис не позволяет.
>
> А почему "увы"? По-моему, да и хрен с ним.

Да по-моему так же.


 
oxffff ©   (2007-09-24 22:29) [121]

Leonid Troyanovsky ©   (24.09.07 17:35) [119]
Джо ©   (24.09.07 20:11) [120]

Конструктивно и выразительно, но непонятно.



Страницы: 1 2 3 4 вся ветка

Текущий архив: 2007.10.21;
Скачать: CL | DM;

Наверх




Память: 0.82 MB
Время: 0.03 c
2-1190688191
Arkadiy
2007-09-25 06:43
2007.10.21
числа в строковом поле


15-1190201963
Kerk
2007-09-19 15:39
2007.10.21
Относится ко многим веткам


4-1176729060
Still Swamp
2007-04-16 17:11
2007.10.21
Как отключить диск в системе.


2-1190532007
San1712
2007-09-23 11:20
2007.10.21
Как записать в реестр параметр типа REG_DWORD ?


9-1161610372
Xdebugger
2006-10-23 17:32
2007.10.21
Глюк при установке GLOXODE