Форум по программированию Delphi Sources

 



Вернуться   Форум по программированию Delphi Sources > Разное > Флейм
Ник
Пароль
Регистрация <<         Правила форума         >> FAQ Пользователи Календарь Поиск Сообщения за сегодня Все разделы прочитаны

Ответ
 
Опции темы Поиск в этой теме Опции просмотра
  #16  
Старый 28.03.2014, 05:31
Аватар для lmikle
lmikle lmikle вне форума
Модератор
 
Регистрация: 17.04.2008
Сообщения: 7,233
Версия Delphi: 7, XE3, 10.2
Репутация: 49087
По умолчанию

Динамические массивы используются, когда заранее неизвестно кол-во элементов. В принципе, для любого типа можно использовать списки, НО! для простых типов, не указателей, надо специально создавать указатель и выделять память, что ведет еще к большей фрагментации памяти. Хотя для динамического массива возможны скрытые расходы на получение нового блока памяти и копирование элементов из старого в новый массив.

А вообще, можно любую синтаксическую конструкцию использовать так, что захочется руки оторвать. И что теперь, минимизировать возможности языков?
Ответить с цитированием
  #17  
Старый 28.03.2014, 08:48
Аватар для Freeman
Freeman Freeman вне форума
Человек-компилятор
 
Регистрация: 05.10.2012
Адрес: Санкт-Петербург
Сообщения: 575
Версия Delphi: 6
Репутация: выкл
По умолчанию

Цитата:
Сообщение от lmikle
И что теперь, минимизировать возможности языков?
Не минимизировать, а упорядочить. Скажем, для динамических массивов не помешал бы какой-нибудь механизм финализации, по типу переопределения операторов, позволяющий вызвать деструктор или каким-нибудь другим способом освободить связанную с элементом массива память.
__________________
Не стоит путать форумы с богадельнями. © Bargest
Ответить с цитированием
  #18  
Старый 28.03.2014, 09:00
Аватар для Aristarh Dark
Aristarh Dark Aristarh Dark вне форума
Модератор
 
Регистрация: 07.10.2005
Адрес: Санкт-Петербург
Сообщения: 2,890
Репутация: выкл
По умолчанию

Цитата:
Сообщение от Freeman
Не минимизировать, а упорядочить. Скажем, для динамических массивов не помешал бы какой-нибудь механизм финализации, по типу переопределения операторов, позволяющий вызвать деструктор или каким-нибудь другим способом освободить связанную с элементом массива память.

Ага, пусть компилятор сам думает. C# получится тогда, или ПыХыПы
__________________
Некоторые программисты настолько ленивы, что сразу пишут рабочий код.

Если вас наказали ни за что - радуйтесь: вы ни в чем не виноваты.
Ответить с цитированием
  #19  
Старый 29.03.2014, 00:16
Аватар для angvelem
angvelem angvelem вне форума
.
 
Регистрация: 18.05.2011
Адрес: Омск
Сообщения: 3,970
Версия Delphi: 3,5,7,10,12,XE2
Репутация: выкл
По умолчанию

Цитата:
Сообщение от Freeman
.. какой-нибудь механизм финализации...
Finalize и SetLength(xx, 0) никто не отменял.
__________________
Je venus de nulle part
55.026263 с.ш., 73.397636 в.д.
Ответить с цитированием
  #20  
Старый 29.03.2014, 02:28
Аватар для Freeman
Freeman Freeman вне форума
Человек-компилятор
 
Регистрация: 05.10.2012
Адрес: Санкт-Петербург
Сообщения: 575
Версия Delphi: 6
Репутация: выкл
По умолчанию

Цитата:
Сообщение от angvelem
Finalize и SetLength(xx, 0) никто не отменял.
Я не проводил опытов, но из справки вижу, что деструкторы в них не вызываются.
__________________
Не стоит путать форумы с богадельнями. © Bargest
Ответить с цитированием
  #21  
Старый 29.03.2014, 04:36
Аватар для angvelem
angvelem angvelem вне форума
.
 
Регистрация: 18.05.2011
Адрес: Омск
Сообщения: 3,970
Версия Delphi: 3,5,7,10,12,XE2
Репутация: выкл
По умолчанию

И не должны, так при создании динамического массива и Create не вызывается. Он просто не существует.
__________________
Je venus de nulle part
55.026263 с.ш., 73.397636 в.д.
Ответить с цитированием
  #22  
Старый 29.03.2014, 09:38
Аватар для M.A.D.M.A.N.
M.A.D.M.A.N. M.A.D.M.A.N. вне форума
Sir Richard Abramson
 
Регистрация: 05.04.2008
Сообщения: 5,501
Версия Delphi: XE10
Репутация: выкл
По умолчанию

Еще раз говорю, у них разная абстракция данных, массивы - это наследие из паскаля, в котором не было понятия объекта.
__________________
— Как тебя понимать?
— Понимать меня не обязательно. Обязательно меня любить и кормить вовремя.


На Delphi, увы, больше не программирую.
Рекомендуемая литература по программированию
Ответить с цитированием
  #23  
Старый 30.03.2014, 00:04
Аватар для Freeman
Freeman Freeman вне форума
Человек-компилятор
 
Регистрация: 05.10.2012
Адрес: Санкт-Петербург
Сообщения: 575
Версия Delphi: 6
Репутация: выкл
По умолчанию

Цитата:
Сообщение от angvelem
при создании динамического массива и Create не вызывается.
Ломать -- не строить, как говорят в народе. Структуры данных и объекты могут создаваться сколь угодно сложно, но способов уничтожения всего два -- FreeMem и TObject.Free. На это намекает и единственность деструктора при широком использовании перегрузки конструкторов.

Поскольку, как тут правильно заметили, динамические массивы могут использоваться и для невладеющих ссылок, достаточно было бы одного ключевого слова, чтобы показать, что ссылка владеющая. Скажем, пусть это будет class:
Код:
type
  TObjects = array of class TObject; // первый вариант

Цитата:
Сообщение от M.A.D.M.A.N.
массивы - это наследие из паскаля, в котором не было понятия объекта.
В теме речь про динамические массивы. К статическим у меня претензий нет. Динамические массивы были добавлены именно в Delphi, да не сразу, а где-то в 3-4-й версии, став расширением реализации AnsiString на произвольный тип данных.
__________________
Не стоит путать форумы с богадельнями. © Bargest
Ответить с цитированием
  #24  
Старый 30.03.2014, 00:16
Аватар для PhoeniX
PhoeniX PhoeniX вне форума
Always hardcore!
 
Регистрация: 04.03.2009
Адрес: СПб
Сообщения: 3,238
Версия Delphi: GCC/FPC/FASM
Репутация: 62149
По умолчанию

Хорошо. Поставим задачу так:
У нас есть какие-то объекты, которые мы как-то создали. И есть массив. Динамический. Мы добавляем в него эти объекты. Созданные ранее. А потом удаляем из этого массива. Вопрос: объекты должны удалиться? Ответ - нет.

Массив - в данном случае просто список чего угодно. array of integer - динамический массив чисел. array of string - динамический массив строк. array of TPoint - динамический массив точек на плоскости (при этом TPoint есть record, а не class).

А array of TObject - это массив объектов. И программист сам должен заботиться о создании и уничтожении этих объектов.
__________________
Оставайтесь хорошими людьми...
VK id2634397, ds [at] phoenix [dot] dj
Ответить с цитированием
  #25  
Старый 30.03.2014, 08:11
Аватар для M.A.D.M.A.N.
M.A.D.M.A.N. M.A.D.M.A.N. вне форума
Sir Richard Abramson
 
Регистрация: 05.04.2008
Сообщения: 5,501
Версия Delphi: XE10
Репутация: выкл
По умолчанию

Не вариант?
Код:
type
  IMyIntf = interface
  ['{D5901C23-79CD-45A7-904B-5966ACE5ACCF}']
  end;

  TMyIntfClass = class(TInterfacedObject, IMyIntf)
  private
  public
    destructor Destroy; override;
  end;

procedure TForm1.btn1Click(Sender: TObject);
var
  foo: array of IMyIntf;
  i: Integer;
begin
  SetLength(foo, 4);
  for i := 0 to 3 do
    foo[i] := TMyIntfClass.Create;
end;

{ TMyIntfClass }

destructor TMyIntfClass.Destroy;
begin
  ShowMessage('destructed');
  inherited;
end;

"К массивам интерфейсов у меня претензий нет" expected;

Код:
procedure _FinalizeArray(p: Pointer; typeInfo: Pointer; elemCount: Cardinal);
{$IFDEF PUREPASCAL}
var
  FT: PFieldTable;
begin
  if elemCount = 0 then Exit;
  case PTypeInfo(typeInfo).Kind of
    tkLString: _LStrArrayClr(P^, elemCount);
    tkWString: _WStrArrayClr(P^, elemCount);
    tkVariant:
      while elemCount > 0 do
      begin
        _VarClr(PVarData(P)^);
        Inc(Integer(P), sizeof(Variant));
        Dec(elemCount);
      end;
    tkArray:
      begin
        FT := PFieldTable(Integer(typeInfo) + Byte(PTypeInfo(typeInfo).Name[0]));
        while elemCount > 0 do
        begin
          _FinalizeArray(P, FT.Fields[0].TypeInfo^, FT.Count);
          Inc(Integer(P), FT.Size);
          Dec(elemCount);
        end;
      end;
    tkRecord:
      begin
        FT := PFieldTable(Integer(typeInfo) + Byte(PTypeInfo(typeInfo).Name[0]));
        while elemCount > 0 do
        begin
          _FinalizeRecord(P, typeInfo);
          Inc(Integer(P), FT.Size);
          Dec(elemCount);
        end;
      end;
    tkInterface:
      while elemCount > 0 do
      begin
        _IntfClear(IInterface(P^));
        Inc(Integer(P), 4);
        Dec(elemCount);
      end;
    tkDynArray:
      while elemCount > 0 do
      begin
        _DynArrayClr(P);
        Inc(Integer(P), 4);
        Dec(elemCount);
      end;
  else
    Error(reInvalidPtr);
  end;
end;

Можно финалайзаррэй на свой подменить.
__________________
— Как тебя понимать?
— Понимать меня не обязательно. Обязательно меня любить и кормить вовремя.


На Delphi, увы, больше не программирую.
Рекомендуемая литература по программированию

Последний раз редактировалось M.A.D.M.A.N., 30.03.2014 в 09:00.
Ответить с цитированием
  #26  
Старый 30.03.2014, 08:33
Аватар для M.A.D.M.A.N.
M.A.D.M.A.N. M.A.D.M.A.N. вне форума
Sir Richard Abramson
 
Регистрация: 05.04.2008
Сообщения: 5,501
Версия Delphi: XE10
Репутация: выкл
По умолчанию

Кстати, попутно в ХЕ5 баг нашел, еще в пятницу на работе обнаружили странное поведение у TValues с объектами, дак вот, смысл в том, что дельфи ХЕ5 класс-наследник от TObject определяет как UString и пытается с ним как со строками работать, соответственно выдает ошибки
__________________
— Как тебя понимать?
— Понимать меня не обязательно. Обязательно меня любить и кормить вовремя.


На Delphi, увы, больше не программирую.
Рекомендуемая литература по программированию
Ответить с цитированием
  #27  
Старый 30.03.2014, 09:16
Аватар для NumLock
NumLock NumLock вне форума
Let Me Show You
 
Регистрация: 30.04.2010
Адрес: Северодвинск
Сообщения: 5,426
Версия Delphi: 7, XE5
Репутация: 59585
Смех

да, странно что компилятор не вызывает конструкторы при инициализации динмассива объектов и деструкторы при финализации. как легко было б программистам
__________________
Пишу программы за еду.
__________________
Ответить с цитированием
  #28  
Старый 30.03.2014, 13:44
Аватар для Freeman
Freeman Freeman вне форума
Человек-компилятор
 
Регистрация: 05.10.2012
Адрес: Санкт-Петербург
Сообщения: 575
Версия Delphi: 6
Репутация: выкл
По умолчанию

Цитата:
Сообщение от PhoeniX
А array of TObject - это массив объектов. И программист сам должен заботиться о создании и уничтожении этих объектов.
Хорошо. Я страшную вещь спрошу: чем динамический массив отличается от статического? Возможностью установки размера во время выполнения, не так ли? И размер ведь можно не только увеличивать, но и уменьшать. Тогда получается, что абсолютно штатный вызов абсолютно штатной SetLength приведет к утечке памяти. Это больше на Си похоже, где в каждой строчке подстава может быть, не?

Цитата:
Сообщение от M.A.D.M.A.N.
"К массивам интерфейсов у меня претензий нет" expected;
К массивам интерфейсов у меня действительно претензий нет, поскольку они управляемы автоматически и потому ведут себя аналогично простым типам. Из-за встроенного счетчика все ссылки на интерфейс являются владеющими, что и придает им сие "волшебное" свойство.

Загвоздка в том, что это мы с тобой знаем про интерфейсы, но не задавальщики вопросов на форумах.
__________________
Не стоит путать форумы с богадельнями. © Bargest
Ответить с цитированием
  #29  
Старый 30.03.2014, 22:36
Аватар для angvelem
angvelem angvelem вне форума
.
 
Регистрация: 18.05.2011
Адрес: Омск
Сообщения: 3,970
Версия Delphi: 3,5,7,10,12,XE2
Репутация: выкл
По умолчанию

Цитата:
Сообщение от Freeman
...вызов абсолютно штатной SetLength приведет к утечке памяти...
А ты посмотри модуль system.pas и поймёшь, что никакой утечки не будет. Если и это не убедит, воспользуйся, к примеру, программой AQTime.
__________________
Je venus de nulle part
55.026263 с.ш., 73.397636 в.д.
Ответить с цитированием
  #30  
Старый 30.03.2014, 23:21
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Freeman
Хорошо. Я страшную вещь спрошу: чем динамический массив отличается от статического? Возможностью установки размера во время выполнения, не так ли? И размер ведь можно не только увеличивать, но и уменьшать. Тогда получается, что абсолютно штатный вызов абсолютно штатной SetLength приведет к утечке памяти. Это больше на Си похоже, где в каждой строчке подстава может быть, не?
Не может SetLength приводить к утечкам памяти - сколько раз её ни вызывай всё равно вся память занимаемая динамическим массивом после его разрушения будет возвращена в общее пользование. Если речь о том, что при этом не происходит разрушения объектов (в случае массива объектов), то это не из-за того что динамические массивы плохие, а из-за того что объекты не являются авторазрушающимися сущностями из-за отсутствия у них счётчика ссылок или другого подобного механизма. Да и не должны разрушаться объекты при разрушении динамического массива - может эти объекты ещё используется в другом месте. Да и статические массивы в этом плане ни чем не отличаются - если в процедуре будет статический массив объектов, то при выходе из этой процедуры ни какие объекты не будут разрушены, но опять же из-за того, что объекты не являются авторазрушаемыми, а вовсе не из-за того, что статические массивы это плохо.
Цитата:
Сообщение от Freeman
К массивам интерфейсов у меня действительно претензий нет, поскольку они управляемы автоматически и потому ведут себя аналогично простым типам. Из-за встроенного счетчика все ссылки на интерфейс являются владеющими, что и придает им сие "волшебное" свойство.
Но при этом они приобретают "волшебное" свойство давать утечки памяти в случае закольцованных ссылок, т.е. если первый экземпляр интерфейса будет ссылаться на второй, а второй на первый, то они не будут авторазрушены даже если на них не будет больше ни одной "внешней" ссылки.
Ответить с цитированием
Ответ



Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск
Опции просмотра

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы не можете редактировать сообщения

BB-коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход


Часовой пояс GMT +3, время: 19:36.


 

Сайт

Форум

FAQ

RSS лента

Прочее

 

Copyright © Форум "Delphi Sources", 2004-2018

ВКонтакте   Facebook   Twitter