среда, 8 апреля 2015 г.

"Новые записи"от EMBT это - БОМБА

"Новые записи"от EMBT это - БОМБА.

По моему скромному мнению.

Просто посмотрите сюда:

Коротко. Слабая ссылка на интерфейс.
https://bitbucket.org/lulinalex/mindstream/commits/bf726c3a47cc61b1216f0085919f5d3633324356.

Ещё бы деструкторы для записей сделали и можно было бы нормальное RAII использовать.

[dcc32 Error] msInterfaces.pas(193): E2465 A record cannot introduce a destructor

А зря... Можно было бы делать AutoPtr'ы в стиле C++.

И тогда бы Delphi был бы крут. Более чем крут.

Хочешь ARC, хочешь "ручное управление".

Хочешь "чёрта лысого" - тоже можно.

6 комментариев:

  1. Вместо "деструктора" можно жеж обычный метод-процедуру использовать? Вместо конструктора, кстати, тоже (конструктору нельзя сказать inline)

    ОтветитьУдалить
    Ответы
    1. Про "обычный метод" - я знаю :-) Я про RAII.Чтобы деструктор автоматом звался. Ничто же не мешает :-)

      Удалить
    2. автоматом - да, было бы очень даже кстати :)
      Но можно же сделать "финт ушами".. если очень захотеть?

      Удалить
    3. Ну что-то типа такого (правда я не очень люблю такие вещи):

      program Project1;

      {$APPTYPE CONSOLE}

      {$R *.res}

      uses
      System.SysUtils;


      type
      PMyRecord = ^TMyRecord;
      TMyRecord = record
      private
      FItf: IUnknown;
      public
      SomeData: string;
      constructor Create(ASomeData: string);
      procedure Destroy;
      end;

      TMyInterface = class(TInterfacedObject)
      FRecord: PMyRecord;
      constructor Create(ARecord: PMyRecord);
      destructor Destroy; override;
      end;

      { TMyRecord }

      constructor TMyRecord.Create(ASomeData: string);
      begin
      WriteLn('TMyRecord.Create');
      FItf := TMyInterface.Create(@Self);
      SomeData := ASomeData;
      end;

      procedure TMyRecord.Destroy;
      begin
      WriteLn('TMyRecord.Destroy');
      end;

      { TMyInterface }

      constructor TMyInterface.Create(ARecord: PMyRecord);
      begin
      WriteLn('TMyInterface.Create');
      FRecord := ARecord;
      end;

      destructor TMyInterface.Destroy;
      begin
      WriteLn('TMyInterface.Destroy');
      if Assigned(FRecord) then
      begin
      FRecord.Destroy;
      FRecord := nil;
      end;
      inherited;
      end;

      procedure Test;
      var
      MyRecord: TMyRecord;
      begin
      MyRecord.Create('SomeData');
      WriteLn('MyRecord.SomeData: ', MyRecord.SomeData);
      end;

      begin
      try
      Test;
      except
      on E: Exception do
      Writeln(E.ClassName, ': ', E.Message);
      end;
      ReadLn;
      end.

      Удалить
    4. Можно, через интерфейсы. Но это "из пушки по воробьям" зачастую.

      Удалить
    5. Вот написал "это", и думаю, смысл тогда делать через record...

      А вообще record'ы мне нравятся, на работе как раз недавно занимался переделкой старых object'ов на оные.

      Удалить