接受任何类型的参数如:布尔值、字符串、浮点数等

问题描述

在这里有这个代码

type  // This Enumerator Type for Handling the Registry Results ...
 TRegistryKind = (rkBOOL,rkSTRING,rkEXPANDSTR,rkINTEGER,rkFLOAT,rkCURRENCY,rkBINARY_DATA,rkDATE,rkTIME,rkDATE_TIME);

 TRegistryKindResult = record
   AsBool: Boolean;
   Asstring: string;
   AsInteger: Integer;
   AsFloat: Single;
   AsCurrency: Currency;
 end;

我需要在这里创建一个带有通用婴儿车的单一程序,该程序接受任何类型的输入类型并将它们保存到注册表中..
这是诀窍:

procedure TAppSettings.Save_Setting_ToRegistry(AKey,AItem_Setting: String;
    AValue: **UnkNownType**; ARegKind: TRegistryKind);
var
  Reg: TRegIniFile;
begin
  Reg := TRegIniFile.Create(AKey);
  try
    case ARegKind of
      rkBOOL: Reg.WriteBool('',AItem_Setting,AValue);
      rkSTRING: Reg.WriteString('',AValue);
    end;

    Reg.CloseKey;
  finally
    Reg.Free;
  end;
end;

我应该为参数 AValue 做什么?有没有一种聪明的方法可以告诉我的 Delphi IDE 接受来自我在上面 TRegistryKindResult 记录中定义的 5 种类型的任何输入?

解决方法

老派的方法是使用 variants。那么,实际上,您甚至不需要 TRegistryKind 参数:

procedure SaveSetting(const AKey,ASetting: string; AValue: Variant);
var
  Reg: TRegistry;
begin
  Reg := TRegistry.Create;
  try
    Reg.RootKey := HKEY_CURRENT_USER;
    if Reg.OpenKey(AKey,True) then
    begin
      case VarType(AValue) of
        varSmallint,varInteger,varShortInt,varByte,varWord:
          Reg.WriteInteger(ASetting,AValue);
        varCurrency:
          Reg.WriteCurrency(ASetting,AValue);
        varSingle,varDouble:
          Reg.WriteFloat(ASetting,AValue);
        varBoolean:
          Reg.WriteBool(ASetting,AValue);
        varString,varUString:
          Reg.WriteString(ASetting,AValue);
      else
        raise Exception.Create('Unsupported variant type.');
      end;
    end;
  finally
    Reg.Free;
  end;
end;

测试:

procedure TForm1.FormCreate(Sender: TObject);
begin
  SaveSetting('Software\Rejbrand\Test','intsetting',123);
  SaveSetting('Software\Rejbrand\Test','cursetting',Currency(3.1415));
  SaveSetting('Software\Rejbrand\Test','fltsetting',Double(3.1415));
  SaveSetting('Software\Rejbrand\Test','boolsetting',True);
  SaveSetting('Software\Rejbrand\Test','strsetting','Hello,World!');
end;
,

这是一个解决方案(过去使用过,但现在未测试):

procedure TAppSettings.Save_Setting_ToRegistry(AKey,AItem_Setting: String;
    const AValue; ARegKind: TRegistryKind);
var
  Reg: TRegIniFile;
  VBool: Boolean absolute AValue;
  VString: String absolute AValue;
  VInteger: Integer absolute AValue;
  VFloat: Single absolute AValue;
  VCurrency: Currency absolute AValue;
begin
  Reg := TRegIniFile.Create(AKey);
  try
    case ARegKind of
      rkBOOL: Reg.WriteBool('',AItem_Setting,VBool);
      rkSTRING: Reg.WriteString('',VString);
      // Manage the other types...
    end;

    Reg.CloseKey;
  finally
    Reg.Free;
  end;
end;