常量`基数'数组产生错误'常量表达式违反了子范围“

问题描述 投票:6回答:2

为什么以下代码:

const
  ANSICOLORS: array of cardinal = [
    $000000,//0
    $800000,//1, compilation error starts with this value
    $008000,//2
    $808000,//3
    $000080,//4
    $800080,//5
    $008080,//6
    $D0D0D0,//7
    $3F3F3F,//8
    $FF0000,//9
    $00FF00,//A
    $FFFF00,//B
    $0000FF,//C
    $FF00FF,//D
    $00FFFF,//E
    $FFFFFF];//F

将在Delphi XE4(win32和win64)下产生以下编译错误:

[dcc32错误] Debug.pas(66):E1012常量表达式违反了子范围边界

$800000范围内的值Cardinal不是吗?

delphi compiler-errors delphi-xe4
2个回答
4
投票

从记忆的角度来看,$800000确实在Cardinal的范围内。

我认为Cardinal($800000)类型转换会修复它,但事实并非如此。

Delphi XE7及以上版本实际上正确编译了您的代码。

这也失败了,直到Delphi XE6出现同样的错误:

const
  CardinalArray: array of Cardinal = [257];

我认为原因是Delphi编译器将[257]视为set,尽管左侧表明它应该是array

这在XE4中失败,但在XE7及以上编译正常:

program Cardinals;

{$APPTYPE CONSOLE}

uses
  System.SysUtils;

const
  CardinalArray: array of Cardinal = [257]; // fails until Delphi XE4 with "E1012 Constant expression violates subrange bounds"

const
  ANSICOLORS: array of Cardinal = [
    $000000,//0
    $800000,//1, compilation error starts with this value
    $008000,//2
    $808000,//3
    $000080,//4
    $800080,//5
    $008080,//6
    $D0D0D0,//7
    $3F3F3F,//8
    $FF0000,//9
    $00FF00,//A
    $FFFF00,//B
    $0000FF,//C
    $FF00FF,//D
    $00FFFF,//E
    $FFFFFF];//F

var
  AnsiColor: Cardinal;

begin
  try
    for AnsiColor in AnsiColors do
      Writeln(Format('$%6.6x', [AnsiColor]));
  except
    on E: Exception do
      Writeln(E.ClassName, ': ', E.Message);
  end;
end.

输出:

$000000
$800000
$008000
$808000
$000080
$800080
$008080
$D0D0D0
$3F3F3F
$FF0000
$00FF00
$FFFF00
$0000FF
$FF00FF
$00FFFF
$FFFFFF

如果您可以使用非动态数组,那么下面的示例适用于Delphi XE4(我早在Delphi 2007上测试它,对于XE和更早版本,您必须用System.SysUtils替换SysUtils))。

注意开关:

  • array of Cardinalarray[0..15] of Cardinal
  • []()
program Cardinals;

{$APPTYPE CONSOLE}

//{$R *.res}

uses
  System.SysUtils;

const
  ANSICOLORS: array[0..15] of Cardinal = (
    $000000,//0
    $800000,//1, compilation error starts with this value
    $008000,//2
    $808000,//3
    $000080,//4
    $800080,//5
    $008080,//6
    $D0D0D0,//7
    $3F3F3F,//8
    $FF0000,//9
    $00FF00,//A
    $FFFF00,//B
    $0000FF,//C
    $FF00FF,//D
    $00FFFF,//E
    $FFFFFF);//F

var
  AnsiColor: Cardinal;

begin
  try
    for AnsiColor in AnsiColors do
      Writeln(Format('$%6.6x', [AnsiColor]));
  except
    on E: Exception do
      Writeln(E.ClassName, ': ', E.Message);
  end;
end.

8
投票

您正在使用XE7中引入的功能。

声明动态数组常量。

Dynamic arrays_Delphi xe7

String-Like_Operations_Supported_on_Dynamic_Arrays


在XE4中,它被评估为一个集合,其中的常数不能超过255。

因此错误E1012 Constant expression violates subrange bounds

通过声明来修复它:

const
  ANSICOLORS: array[0..15] of cardinal = (
    $000000,//0
    $800000,//1, 
    $008000,//2
    $808000,//3
    $000080,//4
    $800080,//5
    $008080,//6
    $D0D0D0,//7
    $3F3F3F,//8
    $FF0000,//9
    $00FF00,//A
    $FFFF00,//B
    $0000FF,//C
    $FF00FF,//D
    $00FFFF,//E
    $FFFFFF);//F
© www.soinside.com 2019 - 2024. All rights reserved.