【问题标题】:Odd compilation error message奇怪的编译错误信息
【发布时间】:2015-08-27 19:14:28
【问题描述】:

以下sn-p,在XE6中

procedure TForm1.Test(CDS : TClientDataSet);
var
  AGuid : TGuid;
  lResult : Longint;
begin
  lResult := SysUtils.CreateGUID(AGuid);
  CDS.InsertRecord([AGuid, '', False]);
end;

产生错误信息

[dcc32 Error] Unit1.pas(73): E2150 Bad argument type in variable type array constructor

Fwiw,在发现这一点时,我试图将我的步骤回溯到编译器生成错误的该例程的先前版本

E2197 Constant object cannot be passed as var parameter 

上线

  lResult := SysUtils.CreateGUID(AGuid);

尽管引发它的事实证明是后续代码中的错误。

【问题讨论】:

  • 你有三个答案,但没有一个能解决你想要解释的问题,根据你对他们每个人的 cmets。这是没有提出问题的结果,您的帖子只是发表声明。
  • @Sertac Akyuz:抱歉,如果我在 q 的标题末尾加上一个问号,可能会更清楚。没有争论的意思,但三个答案设法用“[不,编译器错误消息并不奇怪,因为...]”形式的答案解决了这个隐含的 q,我接受了大卫的答案,因为它最简洁。
  • 三个答案解决了以“for what it isworth”开头的隐含问题。您已经向其中两个提到了 cmets 中的第一个错误,但您接受了一个。现在你说你得到了三个满意的答案。就这样吧。

标签: delphi delphi-xe6


【解决方案1】:

一个 const 数组不能采用 TGuid 记录类型。

一个 const 数组接受定义为的 TVarRec 项:

TVarRec = record
  case Byte of
    vtInteger:    (VInteger: Integer; VType: Byte);
    vtBoolean:    (VBoolean: Boolean);
    vtChar:       (VChar: Char);
    vtExtended:   (VExtended: PExtended);
    vtString:     (VString: PShortString);
    vtPointer:    (VPointer: Pointer);
    vtPChar:      (VPChar: PChar);
    vtObject:     (VObject: TObject);
    vtClass:      (VClass: TClass);
    vtWideChar:   (VWideChar: WideChar);
    vtPWideChar:  (VPWideChar: PWideChar);
    vtAnsiString: (VAnsiString: Pointer);
    vtCurrency:   (VCurrency: PCurrency);
    vtVariant:    (VVariant: PVariant);

【讨论】:

  • 显然不是,但就像我说的那样,我正在尝试(到目前为止没有成功)将我的步骤回溯到我提到的其他编译器错误消息。如果/当我设法做到这一点时,我会更新 q。
【解决方案2】:

数组构造函数中不允许使用 TGuid 类型。

TGuid 声明为:

  TGUID = packed record
    D1: LongWord;
    D2: Word;
    D3: Word;
    D4: array[0..7] of Byte;
    class operator Equal(const Left, Right: TGUID): Boolean;
    class operator NotEqual(const Left, Right: TGUID): Boolean;
    class function Empty: TGUID; static;
  end;

并且根据帮助,数组构造函数中不支持枚举和记录:

... 因为数组构造函数不支持枚举和记录。

如果您想存储 Guid,您应该使用 GuidToString 将其转换为字符串:

CDS.InsertRecord([GUIDToString(AGuid), '', False]);

【讨论】:

  • 您链接到的文档很草率。数组构造函数可以接受记录和枚举类型。据我所知,他们确实可以接受任何类型。但是,可变开放数组参数的数组构造函数不能接受记录。
  • "您应该使用 GuidToString 将其转换为字符串" 确实,但我最初遇到的问题是编译器在 CreateGuid() 上出现我提到的另一个错误消息。
  • OT: TGUID.NewGuid.ToString 创建一个新的 GUID 并将其作为字符串返回(感谢 TGuidHelper)。
【解决方案3】:

这是InsertRecord方法的声明:

procedure InsertRecord(const Values: array of const);

参数是一个变体开放数组。 Variant open array parameters 通过作为 TVarRec 实例传递在内部实现。而TVarRec 不能包含记录。由于TGUID是一条记录,所以不能传入变体开放数组参数。

【讨论】:

  • 谢谢。好好休息后,我将尝试重新创建引起我在此之前遇到的错误的马戏团。通常我在 D7 中做我的 SO 东西以避免最近的 Delphi 怪癖,但我试图绕过 D7 问题,即 TFields 编辑器不会在 TGuidField 上执行“新字段”-它将字段大小设置为“0” ,而应该是 38 岁。哼哼……
猜你喜欢
  • 1970-01-01
  • 2012-05-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-01-22
相关资源
最近更新 更多