将 ToString 用于 Variant 变量
Using ToString for Variant variables
以下代码产生 EVariantInvalidOpError
异常:
var
i : Variant;
begin
i := 10;
ShowMessage(i.ToString());
end;
以下所有工作正常,但我不明白为什么 ToString
函数会引发 Variant
类型变量的异常:
var
i : Variant;
begin
i := 10;
ShowMessage(VarToStr(i));
end;
var
i : Integer;
begin
i := 10;
ShowMessage(i.ToString());
end;
变体让您可以在其中存储各种类型的值,而类型在编译时可能是未知的。您可以将整数值写入 Variant
类型的单个变量,稍后用字符串值覆盖它。除了值变体记录,其中还存储了 type information。在这些值中,其中一些值自动分配 and/or 引用计数。当从 Variant
变量写入或读取值时,编译器在幕后做了很多事情。
varDispatch
类型的变体得到了编译器的更多特殊对待。 varDispatch
表示该值是IDispatch
(usually, but not necessarily related to Windows COM technology类型)。 IDispatch
的实例通过 GetTypeInfoCount
和 GetTypeInfo
方法提供有关其方法和属性的信息。您可以使用其 GetIDsOfNames
方法按名称查询信息。
让我们先回答您评论中的问题:
Why does Delphi allow me to use the ToString
function even if there is no helper implementing such function for the Variant
type?
这就是 Delphi 实现名为 late binding 的概念的方式。它允许您调用编译时类型未知的对象的方法。这个工作的先决条件是底层变体类型支持后期绑定。 Delphi 内置支持 varDispatch
和 varUnknown
变体的后期绑定,如单元 System.Variants
中的过程 DispInvokeCore
所示。
I don't understand why the ToString
function raises exception for Variant
type variables.
如上所述,在 运行 时间,您的程序尝试对变体值调用 ToString
方法,在您的情况下,变体值的类型为 varByte
。由于它不支持后期绑定(以及更多的序数变体类型),您会遇到异常。
要将变量值转换为字符串,请使用 VarToStr
。
这是一个使用 Microsoft Speech 进行后期绑定的简单示例 API:
uses
Winapi.ActiveX,
System.Win.ComObj;
var
Voice: Variant;
begin
CoInitialize(nil);
try
Voice := CreateOleObject('SAPI.SpVoice');
Voice.Speak('Hello, World!');
finally
CoUninitialize;
end;
end.
以下代码产生 EVariantInvalidOpError
异常:
var
i : Variant;
begin
i := 10;
ShowMessage(i.ToString());
end;
以下所有工作正常,但我不明白为什么 ToString
函数会引发 Variant
类型变量的异常:
var
i : Variant;
begin
i := 10;
ShowMessage(VarToStr(i));
end;
var
i : Integer;
begin
i := 10;
ShowMessage(i.ToString());
end;
变体让您可以在其中存储各种类型的值,而类型在编译时可能是未知的。您可以将整数值写入 Variant
类型的单个变量,稍后用字符串值覆盖它。除了值变体记录,其中还存储了 type information。在这些值中,其中一些值自动分配 and/or 引用计数。当从 Variant
变量写入或读取值时,编译器在幕后做了很多事情。
varDispatch
类型的变体得到了编译器的更多特殊对待。 varDispatch
表示该值是IDispatch
(usually, but not necessarily related to Windows COM technology类型)。 IDispatch
的实例通过 GetTypeInfoCount
和 GetTypeInfo
方法提供有关其方法和属性的信息。您可以使用其 GetIDsOfNames
方法按名称查询信息。
让我们先回答您评论中的问题:
Why does Delphi allow me to use the
ToString
function even if there is no helper implementing such function for theVariant
type?
这就是 Delphi 实现名为 late binding 的概念的方式。它允许您调用编译时类型未知的对象的方法。这个工作的先决条件是底层变体类型支持后期绑定。 Delphi 内置支持 varDispatch
和 varUnknown
变体的后期绑定,如单元 System.Variants
中的过程 DispInvokeCore
所示。
I don't understand why the
ToString
function raises exception forVariant
type variables.
如上所述,在 运行 时间,您的程序尝试对变体值调用 ToString
方法,在您的情况下,变体值的类型为 varByte
。由于它不支持后期绑定(以及更多的序数变体类型),您会遇到异常。
要将变量值转换为字符串,请使用 VarToStr
。
这是一个使用 Microsoft Speech 进行后期绑定的简单示例 API:
uses
Winapi.ActiveX,
System.Win.ComObj;
var
Voice: Variant;
begin
CoInitialize(nil);
try
Voice := CreateOleObject('SAPI.SpVoice');
Voice.Speak('Hello, World!');
finally
CoUninitialize;
end;
end.