powered by simpleCommunicator - 2.0.59     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Delphi [игнор отключен] [закрыт для гостей] / Автоматическое уничтожение объектов
25 сообщений из 54, страница 1 из 3
Автоматическое уничтожение объектов
    #40057743
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Реализовал (по работе) механизм, который позволяет автоматически уничтожать объекты. Избавляет от необходимости использования try..finally для удаления объектов.
Пример кода:
Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
procedure Test;
var
  h: TSmartHolder;
  L: TList;
  ini: TIniFile;
  sl: TStrings;
begin
  L := h.CreateList(); // Создание типового объекта
  // далее используем переменную L как обычно

  h.RegObj(ini, TIniFile.Create('myfile.ini')); // Создание произвольного объекта
  // далее используем переменную ini как обычно

  sl := h.RegObj(TStringList.Create) as TStrings; // Создание произвольного объекта
end;



TSmartHolder - это простейший рекорд с единственным полем (интерфейсная ссылка).
Соответственно, все объекты будут уничтожены, как только интерфейсная ссылка будет обнулена, т.е. при выходе рекорда из области видимости.
Работает, начиная с Delphi 2007.
На мой взгляд, штука очень удобная.

Если есть интерес, я могу это оформить на своём аккаунте в гитхабе в виде отдельного модуля.
С другой стороны, не исключаю, что вариантов реализации данного велосипеда уже множество (но мне до сих пор не попадалось) :)
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057771
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Умный указатель через reference to function интереснее... там даже подсказчик кода работает и синтаксис использования не меняется, кроме объявления...
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057775
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
X-Cite
Умный указатель через reference to function интереснее... там даже подсказчик кода работает и синтаксис использования не меняется, кроме объявления...


Где посмотреть на это?
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057779
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
DmSer
TSmartHolder - это простейший рекорд с единственным полем (интерфейсная ссылка).
Тогда ты ее постоянно перезаписываешь. Или там у тебя какой-то IInterfacedList?
DmSer
На мой взгляд, штука очень удобная.
Если изменить требование D2007 на D2009, то RegObj можно объявить дженерик методом и уйти от каста
Код: pascal
1.
function RegObj<T: class>(const AVal: T): T;


DmSer
На мой взгляд, штука очень удобная.
Иногда последовательность уничтожения объектов важна.
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057785
rgreat
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ИМХО это не красиво и не очень удобно.

Не надо связываться с интерфейсами, где это явно не требуется.

В конце концов если сильно хочется - используй рекорды. Благо там теперь и конструктор с деструктором есть.
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057787
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Тогда ты ее постоянно перезаписываешь. Или там у тебя какой-то IInterfacedList?

Там объект, который хранит список зарегистрированных объектов в TList. Объект реализует интерфейс. В рекорде хранится интерфейсная ссылка на этот объект.

Если изменить требование D2007 на D2009, то RegObj можно объявить дженерик методом и уйти от каста

Можно, как вариант.

Иногда последовательность уничтожения объектов важна

Разные ситуации бывают, конечно.
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057791
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
rgreat
ИМХО это не красиво и не очень удобно.

Не надо связываться с интерфейсами, где это явно не требуется.

В конце концов если сильно хочется - используй рекорды. Благо там теперь и конструктор с деструктором есть.


В коде нет явной работы с интерфейсами (см. пример в начале). Всё спрятано в методы рекорда. Интерфейсная ссылка объявлена как private.
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057793
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
  ISmartPointer<T: class> = reference to function: T;

  TSmartPointer<T: class> = class(TInterfacedObject, ISmartPointer<T>)
  strict private
    FObject: T;
    function Invoke: T; inline;
  public
    constructor Create(const aObject: T);
    destructor Destroy; override;
  end;



Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
{ TSmartPointer<T> }

function TSmartPointer<T>.Invoke: T;
begin
  Exit(FObject);
end;

constructor TSmartPointer<T>.Create(const aObject: T);
begin
  FObject := aObject;
end;

destructor TSmartPointer<T>.Destroy;
begin
  FreeAndNil(FObject);
  inherited Destroy();
end;

procedure TForm2.Button1Click(Sender: TObject);
var
  x: ISmartPointer<TForm2>;
begin
  x := TSmartPointer<TForm2>.Create(TForm2.Create(nil));
  x.Caption := '123';
  x.ShowModal();
end;



В последних версиях сломали правда CodeInsight...
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057795
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Использование RegObj выглядит не очень красиво. К сожалению. Тут ничего не поделаешь.
Но такой код смотрится вполне прилично:

Код: pascal
1.
var L := h.CreateStringList();



можно так:
Код: pascal
1.
2.
var L := TStringList.Create();
h.RegObj(L);



У меня в коде есть классы, которые я чаще всего использую (назовём их "типовые классы"). Для них сделал функции создания объекта (CreateStringList, CreateList и т.п.). Иногда добавляю новые функции по мере необходимости. Но это свой фирменный велосипед :)
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057796
alekcvp
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
X-Cite,

Код: pascal
1.
2.
3.
4.
5.
destructor TSmartPointer<T>.Destroy;
begin
  FreeAndNil(FObject);
  inherited Destroy();
end;


Зачем?.. Почему не Free?

Ну и каждое обращение к переменной - вызов функции, ну такое себе. Хотя надо смотреть как компилятор вызов заинлайнит.
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057805
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
alekcvp,

Да все равно... Можно и Free
Ну это уже проблемы компилятора, если он не сможет заинлайнить))) За сомнительное удобство, не из коробки, надо платить...
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057807
Kazantsev Alexey
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
alekcvp
Хотя надо смотреть как компилятор вызов заинлайнит.

Это же интерфейс, откуда там инлайну взяться. Однако, прикольное колдунство :)
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057815
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
var
x: ISmartPointer<TForm2>;
begin
x := TSmartPointer<TForm2>.Create(TForm2.Create(nil));

Не заметил особого преимущества по сравнению с

Код: pascal
1.
2.
3.
4.
5.
var
  x: TForm2;
  h: TSmartHolder;
begin
  x := h.RegObj(TForm2.Create(nil)) as TForm2;



А пытаться понять как работает ISmartPointer - ещё сложнее, чем разобраться с фильмом Довод :)
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057819
Kazantsev Alexey
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
DmSer
Не заметил особого преимущества

Если правильно помню, эту запись:
Код: pascal
1.
x := TSmartPointer<TForm2>.Create(TForm2.Create(nil));


можно сократить до:
Код: pascal
1.
x := TSmartPointer.Create(TForm2.Create(nil));


или вообще создание смартпоинтера завернуть в функцию, например:
Код: pascal
1.
x := Auto(TForm2.Create(nil));
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057828
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Kazantsev Alexey
можно сократить до:
Нельзя.
1. TSmartPointer и TSmartPointer<T> - это разные типы.
2. Можно было бы писать
Код: pascal
1.
x := TSmartPointer<>.Create(TForm2.Create(nil));

но это вам не джава и автовывод типов сюда не завезли
Kazantsev Alexey
или вообще создание смартпоинтера завернуть в функцию,
Нельзя. Дженерик-функций не бывает
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057836
Kazantsev Alexey
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Нельзя.
1. TSmartPointer и TSmartPointer<T> - это разные типы.

Верно, только не специализированных дженериков не бывает.

_Vasilisk_
но это вам не джава и автовывод типов сюда не завезли

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

_Vasilisk_
Нельзя. Дженерик-функций не бывает

А это я с FPC спутал, там они есть :)
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057843
kealon(Ruslan)
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
DmSer,

в любом случае если у тебя появляется AS, значит код уже сразу выглядит аналогично тому как звучит
нельзя использовать хаки везде подряд, карма портится
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057846
kealon(Ruslan)
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Kazantsev Alexey
можно сократить до:
Нельзя.
1. TSmartPointer и TSmartPointer<T> - это разные типы.
2. Можно было бы писать
Код: pascal
1.
x := TSmartPointer<>.Create(TForm2.Create(nil));

но это вам не джава и автовывод типов сюда не завезли
Kazantsev Alexey
или вообще создание смартпоинтера завернуть в функцию,
Нельзя. Дженерик-функций не бывает
как вариант можно хелпером к TObject, мало уже кто функции пишет чистые
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057848
DmSer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
kealon(Ruslan)
DmSer,

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


Мы пока на D2007 работаем. Деваться некуда :))
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057869
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Нельзя. Дженерик-функций не бывает


Бывают)
Код: pascal
1.
2.
3.
4.
  TStatic = class
  public
    class function Test<T: class>(const aObj: T): T; static;
  end;


Например так :)
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057871
Фотография X-Cite
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
А вообще в Spring 4D реализованы smart pointers на вкус и цвет..

Код: pascal
1.
2.
3.
4.
5.
6.
7.
  {$REGION 'Shared smart pointer'}

  IShared<T> = reference to function: T;

  {$REGION 'Weak smart pointer'}

  IWeakReference<T> = interface
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057943
Фотография X11
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
X-Cite
Да все равно... Можно и Free


а если останется ссылка и ты будешь проверять и обращаться? будет AV
думаю, FreeAndNil - правильный всегда вариант
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057956
alekcvp
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
X11
X-Cite
Да все равно... Можно и Free

а если останется ссылка и ты будешь проверять и обращаться? будет AV
думаю, FreeAndNil - правильный всегда вариант

Какая ссылка, если речь идёт о деструкторе?.. Если у тебя после этого останется ссылка, к которой ты будешь обращаться, то ты ССЗБ.
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057964
Фотография X11
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
после Free остается ссылка
не зря ведь придумали FreeAndNil

Код: pascal
1.
2.
3.
4.
o := TObject.Create;
o.Free;

if Assigned(o) then o.Width := 10;



По идее Assigned(o) вернет True
...
Рейтинг: 0 / 0
Автоматическое уничтожение объектов
    #40057970
rgreat
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
X11
после Free остается ссылка
не зря ведь придумали FreeAndNil

Код: pascal
1.
2.
3.
4.
o := TObject.Create;
o.Free;

if Assigned(o) then o.Width := 10;



По идее Assigned(o) вернет True

А не надо так делать.

Вообще с Assigned надо быть очень аккуратным и точно знать как работает то что туда передаешь.
Ибо если не уверен на 100% что в o может быть либо живой объект либо nil то Assigned применять вообще нельзя.
...
Рейтинг: 0 / 0
25 сообщений из 54, страница 1 из 3
Форумы / Delphi [игнор отключен] [закрыт для гостей] / Автоматическое уничтожение объектов
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]