2016-07-15 7 views
7

У меня есть этот код в библиотеке Delphi Detours, который я пытаюсь порт:Delphi ключевое слово «по умолчанию» с типами записей в старых версиях Delphi

type 
    TInstruction = record 
    Archi: Byte; { CPUX32 or CPUX64 ! } 
    AddrMode: Byte; { Address Mode } 
    Addr: PByte; 
    VirtualAddr: PByte; 
    NextInst: PByte; { Pointer to the Next Instruction } 
    OpCode: Byte; { OpCode Value } 
    OpType: Byte; 
    OpKind: Byte; 
    OpTable: Byte; { tbOneByte,tbTwoByte,... } 
    OperandFlags: Byte; 
    Prefixes: Word; { Sets of Prf_xxx } 
    ... 
    end; 

var 
    Inst: TInstruction; 
begin 
    ... 
    Inst := default (TInstruction); // <- 
    Inst.Archi := CPUX; 
    Pvt := PPointer(AIntf)^; // vTable ! 
    PCode := PPointer(Pvt + Offset)^; // Code Entry ! 
    Inst.NextInst := PCode; 
    ... 
end; 

Что означает «default» ключевое слово делать? я предположить что-то вроде:

FillChar(Inst, SizeOf(TInstruction), 0); 

Является ли мое предположение верно?

+0

Он завершает/инициализирует поля управляемых типов. –

+0

@ LURD, я могу понять, что «инициализирует» часть. но когда это завершает переменную? – zig

+0

@zig, например, очистка памяти от динамических массивов и укусов, если удаленная запись была последней ссылкой. Другим примером является отключение объектов, связанных со списком типов интерфейса. см. docwiki.embarcadero.com/Libraries/XE7/en/System.Finalize –

ответ

13

Default() - недокументированная внутренняя функция, введенная для поддержки дженериков. Дизайн дженериков Delphi был в большой степени вдохновлен генераторами .net, и вам может быть полезно прочитать документацию по аналогам .net: https://msdn.microsoft.com/en-GB/library/xwth0h0d.aspx

Цель Default() - разрешить вам инициализировать переменную по умолчанию. При работе с общими типами Default() вы можете сделать это для переменной, тип которой является общим.

Если вы хотите, чтобы воспроизвести поведение Default() сделать следующее:

Finalize(Inst); 
FillChar(Inst, SizeOf(Inst), 0); 

Вызов Finalize требуется в случае, если тип управляется. То есть, если тип управляется или содержит какие-либо элементы, которые управляются. Управляемые типы включают строки, динамические массивы, интерфейсы, варианты, анонимные методы и т. Д.

Если тип не содержит управляемых типов, то вызов Finalize может быть опущен. Это не помешает включить его, потому что компилятор устранит его, если не понадобится. Если вы можете быть на 100% уверены, что никаким управляемым типам не присвоено значение, вы также можете опустить этот вызов.

По умолчанию инициализации означает следующее:

  • Ноль для числовых типов.
  • Значение с порядковым нулем для перечисленных типов.
  • False для булевых типов.
  • #0 для типов символов.
  • Пустая строка для строк.
  • Пустой вариант для Variant.
  • nil для классов, динамических массивов, интерфейсов и анонимных методов.
+0

Подсказка компилятора: '[Подсказка] DDetours.pas (1919): Expression не нуждается в инициализации/завершении'. Итак, нужно ли просто удалить «Finalize (Inst)» или отключить подсказку? – zig

+0

До вас. Сделайте это в любом случае. Вероятно, я удалю Finalize. –