C# 间歇性“;InteropServices.COMException/ForwardCallToInvokeMember”;访问范围单元格上的值2

C# 间歇性“;InteropServices.COMException/ForwardCallToInvokeMember”;访问范围单元格上的值2,c#,excel,excel-dna,C#,Excel,Excel Dna,在我的最后一个问题中: 我将Value2抛出COMException的原因归咎于ExcelDNA。但我不确定这种情况是否会持续下去 我禁用了IsMacroType标志,它完全阻止了COMException的发生,并注意到有时候Range.Value2根本不会引发异常 因此,有时它起作用,有时不起作用。我的问题是,是什么导致range.Value2抛出间歇性ComException 这很烦人,因为stacktrace没有给我任何有用的信息,而IsMacroType完全解决了这个问题 我的怀疑是,如

在我的最后一个问题中:

我将Value2抛出COMException的原因归咎于ExcelDNA。但我不确定这种情况是否会持续下去

我禁用了IsMacroType标志,它完全阻止了COMException的发生,并注意到有时候Range.Value2根本不会引发异常

因此,有时它起作用,有时不起作用。我的问题是,是什么导致range.Value2抛出间歇性ComException

这很烦人,因为stacktrace没有给我任何有用的信息,而IsMacroType完全解决了这个问题

我的怀疑是,如果一个单元格不断变化,在访问Value2时,该单元格可能会失效,但这只是猜测,我不确定excel是如何工作的

但是,它也没有意义,因为代码中没有多个线程

你遇到过这个问题吗

代码如下:

var valueCell = (Range)row.Cells[1, 30];
if (valueCell .Value2 != null)
{
     //do something
}

说真的,Value2无法对if语句求值

我有点惊讶它在没有
IsMacroType=true的情况下还能工作。这可能取决于单元格是否已计算

Excel通常阻止UDF读取工作表的其他部分,除非UDF注册为“宏工作表等效项”(注册字符串中带有#)

注册为“宏工作表等价物”的函数具有以下行为(请参见下表):

在pxTypeText中的最后一个参数代码后面放置一个#字符,使函数具有与宏工作表中函数相同的调用权限。详情如下:

  • 该函数可以检索在此重新计算周期中尚未计算的单元格值

  • 该函数可以调用任何XLM信息(类2)函数,例如xlfGetCell

  • 如果数字符号(#)不存在:对未计算的单元格求值会导致xlretUncalced错误,计算完单元格后将再次调用当前函数;调用xlfCaller以外的任何XLM信息函数都会导致xlretInvXlfn错误

在没有
IsMacroType=true
的情况下,您的错误可能是最后一个错误-您正在读取一个未计算的单元格,因此得到一个错误

为UDF设置
IsMacroType=true
的副作用并不完全清楚。一个效果是,注册为
IsMacroType=true
且具有标记为
AllowReference=true
的参数的函数将自动被视为易失性函数(即使注册为
IsVolatile=false
)。另一个副作用是重新计算顺序受到影响,特别是当您从UDF内部读取未计算的单元格时

在从UDF中读取其他单元格时,您还必须非常小心,考虑到您对何时应该重新计算的预期,因为这样会破坏计算依赖关系树。在您的示例中,您的UDF正在读取单元格A30,但对单元格A30的更改是否会自动导致您的函数重新计算?当然,您不能使用Excel依赖项跟踪工具来理解您的单元格依赖于
A30
。实际上,您更希望有一个接受显式参数的函数,该函数被称为
=DoSomething(A30)
,使所有内容都清晰明了并避免所有这些问题

您可能尝试读取
Value2
的一个原因是确定单元格的格式,而不是Excel存储的基础值,但这确实很危险,因为它不是重新计算和依赖关系树的一部分


因此,我想说,你看到一些意想不到的行为,这表明你正朝着Excel不喜欢的方向前进。

我想我理解你所说的一些内容。“在从UDF读取其他单元格时,您还必须非常小心,考虑到您对何时应该重新计算的期望,因为您有点破坏了计算依赖关系树”-我不记得设置了这个。依赖关系树是如何创建的<代码>A30
,它本身不会改变,但它是一个公式,如果有帮助的话,它会将范围参数作为输入。