为什么可变记录会报告它应该报告的更大的大小?

Why variable records reports bigger size that it should?

我试过这段代码:

  TDairyItemType = (dtFood, dtRecipe, dtExercise);
  TFourDecimalDWord = DWord;

  TDiaryItem = record
   ID: DWord;  // 4 bytes
   Positive: Boolean; // 1 byte
   GID: Word;  // 2 bytes
  case ItemType: TDairyItemType of  // 1 byte
   dtFood, dtRecipe: (ServID: Word; Serving: TFourDecimalDWord); // 6 bytes
   dtExercise: (Time: Word; Kcal: TFourDecimalDWord); // 6 bytes
  end;

procedure TForm1.Button1Click(Sender: TObject);
var Item: TDiaryItem;
begin
  Item.ServID:= 333;
  Caption:= 'Item size: '+IntToStr(SizeOf(TDiaryItem))+'  /  Item.Time: '+IntToStr(Item.Time);
end;

这表明记录的大小是 20,但应该是 14,因为记录的最后两行使用相同的 space。我为 ServID 字段分配了一个值,我从 Time 字段读取它,它确认它们共享相同的 space...我错过了什么?

对齐会增加额外的字节。使用 packed 删除它们,它在这里显示为 14 个字节。

procedure TForm1.Button1Click(Sender: TObject);
type
  TDairyItemType = (dtFood, dtRecipe, dtExercise);
  TFourDecimalDWord = DWord;

  TDiaryItem = packed record
   ID: DWord;  // 4 bytes
   Positive: Boolean; // 1 byte
   GID: Word;  // 2 bytes
  case ItemType: TDairyItemType of  // 1 byte
   dtFood, dtRecipe: (ServID: Word; Serving: TFourDecimalDWord); // 6 bytes
   dtExercise: (Time: Word; Kcal: TFourDecimalDWord); // 6 bytes
  end;

begin
  button1.Caption:= 'Item size: '+IntToStr(SizeOf(TDiaryItem));
end;