将<T>类型的值转换为Variant,是否可能?

Wod*_*dzu 6 delphi generics delphi-2009 variant

这是一个片段,展示了我想要实现的目标:

type
  TMyObject<T> = class (TObject)
    function GetVarType(Value: T): TVarType;
  end;


function TMyObject<T>.GetVarType(Value: T): TVarType;
var
  TmpValue: Variant;
begin
  TmpValue := Variant(Value); //Invalid typecast
  Result := VarType(TmpValue);
end;
Run Code Online (Sandbox Code Playgroud)

我知道上面的类型转换是天真的,但我希望你能得到这个想法.我想用一些转换机制替换它.

TMyObject将始终是简单类型,如Integer,String,Single,Double.

这种转换的目的是函数VarType为每个我可以存储在其他地方的简单类型提供整数常量.

我想知道这种转换是否可行?

谢谢你的时间.

gab*_*abr 7

它在Delphis中可以通过增强的RTTI(2010年及更新版本)轻松解决.太糟糕了,你只限于2009年:(

function TMyObject<T>.GetVarType(Value: T): TVarType;
begin
  Result := VarType(TValue.From<T>(Value).AsVariant);
end;
Run Code Online (Sandbox Code Playgroud)

这仅适用于简单类型,但这是问题中指定的约束.


RRU*_*RUZ 6

您可以使用RTTI获取此信息,只需检查TTypeInfo.Kind属性的值:

检查此示例代码

{$APPTYPE CONSOLE}

uses
  TypInfo,
  Variants,
  Generics.Collections,
  SysUtils;

type
  TMyObject<T> = class (TObject)
    function GetVarType(Value: T): TVarType;
  end;


function TMyObject<T>.GetVarType(Value: T): TVarType;
begin
  Case PTypeInfo(TypeInfo(T))^.Kind of
    tkInteger : Result:=varInteger;
    tkFloat   : Result:=varDouble;
    tkString  : Result:=varString;
    tkUString : Result:=varUString;
    //add more types here
  End;
end;

Var
  LObj : TMyObject<Integer>;
begin
  try
     Writeln(VarTypeAsText(TMyObject<Integer>.Create.GetVarType(5)));
     Writeln(VarTypeAsText(TMyObject<String>.Create.GetVarType('Test')));
  except
    on E: Exception do
      Writeln(E.ClassName, ': ', E.Message);
  end;
  Readln;
end.
Run Code Online (Sandbox Code Playgroud)

这将回来

Integer
UnicodeString
Run Code Online (Sandbox Code Playgroud)