在VBA中无限和超越

tpa*_*ale 28 .net excel vba excel-vba

这篇文章是关于.NET NaN和Inifinite值传递回Excel 2010 VBA.

我使用不受我控制的C#方法(显然)可以返回.NET NaN或Neg,Pos Infinity.VBA中的结果很奇怪(比通常更奇怪),而我能够安全地处理这种情况的唯一方法是一个不优雅的三字符串比较"-1.#IND"或"-1.#INF"或"1.#INF".

有没有更好的办法?

如果你好奇,我已经在这里记录了奇怪的部分.(这些例子是针对NaN的,但对于pos或neg infinity来说也是如此.)

double  dVal  =  CSharpMethodReturningDouble()  ' via .NET assembly / COM interop
variant vVal  =  CSharpMethodReturningDouble()  ' via .NET assembly / COM interop
Run Code Online (Sandbox Code Playgroud)

如果C#方法返回double.NaN,那么我们(在immed窗口中):

?dVal               
 -1.#IND            
?vVal                
 -1.#IND             
Run Code Online (Sandbox Code Playgroud)

持有NaN的(盒装)变体对数字测试为正,type = double

?IsNumeric(vVal) 
 True
?TypeName(vVal)
 Double
Run Code Online (Sandbox Code Playgroud)

比较(盒装)变体NaN的工作,但你得到的结果相反.对(未装箱的)双打进行比较会导致溢出异常

?vVal=1          '<== NaN comparisons should always return false
 True               
?vVal=0          '<== that's not what you get with -1.#IND
 True               
?dVal=0          '<== strangely, the same comparison on the unboxed double fails
 (OverFlow Exc)
Run Code Online (Sandbox Code Playgroud)

(盒装)变量的操作导致溢出异常(未装箱的)操作加倍工作(并返回-1.#IND,如预期的那样)

?vVal * 1.1      '<== even stranger, for arith ops its the boxed value that fails
 (Overflow Exc)
?dVal * 1.1      '<== but the operation on the unboxed double goes through
-1.#IND 
Run Code Online (Sandbox Code Playgroud)

IsError,IsNumeric无济于事:

?IsError(vVal)
 False            
?IsError(dVal)
 False            
?IsNumeric(vVal)
 True       
?IsNumeric(dVal)
 True            
Run Code Online (Sandbox Code Playgroud)

始终可以使用字符串比较来测试:

?vVal = "-1.#IND"
True
?dVal = "-1.#IND"
True
Run Code Online (Sandbox Code Playgroud)

小智 2

由于 Double.NAN 字段表示的值不是数字,因此使用字符串比较很可能是正确的。

如果您采用其他方式(即从 VB 中传递值),则通常会怀疑 ByRef 和 ByVal。

VB 的 IsNumeric() 函数并不总是直观的。例如,如果字母数字代码碰巧是科学记数法中的数字,它将返回 True。