这篇文章是关于.NET NaN的& Inifinite值将传递回Excel 2010 VBA。
我使用不受我控制的C#方法(显然)可以返回.NET NaN或Neg,Pos Infinity。 VBA中的结果很奇怪(比通常更奇怪),而我能够安全地处理这种情况的唯一方法是一个不优雅的三字符串比较“-1。#IND”或“-1。#INF”或“1.#INF”。
有更好的方法吗?
如果你很好奇,我在这里记录了这个奇怪的部分。 (这些例子是针对NaN的,但对于pos或neg无穷大来说也是如此。)
double dVal = CSharpMethodReturningDouble() ' via .NET assembly / COM interop
variant vVal = CSharpMethodReturningDouble() ' via .NET assembly / COM interop
如果C#方法返回double.NaN,那么我们(在immed窗口中):
?dVal
-1.#IND
?vVal
-1.#IND
持有NaN的(盒装)变体测试为数字为正,type = double
?IsNumeric(vVal)
True
?TypeName(vVal)
Double
对(盒装)变体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)
(盒装)变体的操作会导致溢出异常 对(未装箱的)双打的操作起作用(并返回-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
IsError,IsNumeric不起作用:
?IsError(vVal)
False
?IsError(dVal)
False
?IsNumeric(vVal)
True
?IsNumeric(dVal)
True
始终可以使用字符串比较来测试:
?vVal = "-1.#IND"
True
?dVal = "-1.#IND"
True
答案 0 :(得分:2)
由于Double.NAN字段表示的值不是数字,因此您很可能使用字符串比较在正确的轨道上。
如果你走另一条路(即从VB传递值),ByRef和ByVal是常见的嫌疑人。
VB的IsNumeric()函数并不总是直观的。例如,如果字母数字代码偶然发生在科学记数法中,它将返回True。
答案 1 :(得分:1)
我同意David的观点,即您当前的解决方法是可以接受的。一定要测试外语安装!
您提供的示例可能是解决方案的一部分:同时等于1且为0的值不是正常数字。该测试可以将NaN与正常数字区分开来。可能你可以找到这样的类似规则来找到+/-无穷大。
答案 2 :(得分:0)
确保考虑当前的区域设置。
根据小数分隔符设置,NaN可以是"-1.#IND"
或"-1,#IND"
。
避免这种情况的一种方法可能是InStr比较:
InStr(CStr(dVal), "#IND") <> 0