【问题标题】:Type promotion of overloaded function's argument重载函数参数的类型提升
【发布时间】:2015-03-30 16:56:33
【问题描述】:

考虑以下代码:

program Promote;

{$APPTYPE CONSOLE}

uses
  SysUtils;

{$HINTS OFF}

type
  MyWord = record
    FValue: LongWord;
    class operator Implicit(AValue: LongWord): MyWord;
  end;

class operator MyWord.Implicit(AValue: LongWord): MyWord;
begin
  Result.FValue:= AValue;
end;

procedure Test(AValue: MyWord); overload;
begin
  Writeln('MyWord');
end;

procedure Test(AValue: UInt64); overload;
begin
  Writeln('UInt64');
end;

var
  LW: LongWord;

begin
  Test(LW);
  Readln;
end.

当我运行它(Delphi XE)时,我看到编译器将LongWord 参数提升为UInt64(内置类型),而不是MyWord(用户定义类型)。

如果这种提升是在编译器本身中实现的,我是否可以假设 Delphi 编译器总是将内置类型提升为内置类型?

更一般地说,在这种情况下控制类型提升的规则是什么(比如我们有 2 个内置类型,或 2 个用户定义类型等)?

【问题讨论】:

  • 祝你好运。不存在文档。你能做的最好的就是扭转它。
  • 我会期望它总是最近的类型
  • @Sir 写下来很容易,但是没有最接近的精确定义,这是什么意思。我发现重载解决的规则没有充分记录,这真的很令人沮丧。
  • 现在,确实需要澄清什么是内在类型。我认为这些是由语言而不是运行时库定义的。因此,这些类型像 System.IntegerSystem.Double 表面上是 System 单元的一部分,但实际上是语言内置或固有的。我确实想知道这些类型的完整列表是什么。这一切我只能从观察中说出来。
  • 编译器的首选始终是保留调用中传递的实际参数值的过程。当不止一个过程满足上述条件时,可以观察到:编译器更喜欢内置类型而不是用户定义和签名而不是无符号。

标签: delphi type-promotion


【解决方案1】:

据我了解,像uint64 这样的序数类型总是比record 更接近另一个像longword 这样的序数类型。期间。

“更近的类型”距离与“内置”或“自定义”类型无关。你在比较苹果和橘子。

在编译器中,记录和序数是两个不同的家族。您可以定义隐式转换的事实永远不会将 record 提升为序数类型。

因此,“内置”stringinteger 的亲和力总是低于新的序数类型,例如:

type TMyInteger64 = type Int46;

这里,这个TMyInteger64 类型将比内置的string 类型“更接近”。

一旦您定义了 record,它将与其他 record 有关联,而不是序数类型。

【讨论】:

    猜你喜欢
    • 2018-02-19
    • 2023-03-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多