如何检测Excel工作簿是否已关闭(使用C#中的Interop)
本文关键字:使用 Interop 中的 工作簿 何检测 检测 Excel 是否 | 更新日期: 2023-09-27 18:25:24
我正在处理一个C#项目,该项目使用Microsoft.Office.Interop.Excel.Application
从Excel文件中读取值:
try {
Application xlApp = new Application();
Workbook workbook = xlApp.Workbooks.Open(filename)
// ... Load Excel values ...
} finally {
// ... Tidy up ...
}
在finally
块中,我想确保所有内容都已关闭并正确处理,这样内存中就不会有任何内容挂起,Excel也会干净地关闭。已经看到了关于这个代码应该是什么样子的各种线程(比我想象的更复杂!),但它可能包括一件事:
if (workbook != null) {
workbook.Close();
// ... possibly also Marshal.FinalReleaseComObject(workbook);
}
但是,如果工作簿已经关闭,这会引发错误,那么我如何安全地检查它?如果可能的话,我宁愿不只是捕捉错误,因为这种类型的事情往往会扭曲调试。有没有一种干净的方法可以在关闭之前找到工作簿的状态?
还有一个问题是,如果xlApp.Quit();
在之后完成,是否需要workbook.Close()
?退出Excel应用程序会导致workbook.Close()
(以及任何COM对象释放)隐式发生吗?
打开工作簿时,最好的建议是跟踪工作簿并在适当的时候关闭它。如果您的代码非常详细,那么您可以存储一个Boolean
值,指示文件当前是打开还是关闭。
在Excel中没有像IsOpen这样的属性。您可以尝试参考工作簿:
Workbook wbTest = xlApp.Workbooks.get_Item("some.xlsx");
但如果书没有打开,这会产生COM错误,因此会变得非常混乱。
相反,创建您自己的函数IsOpen
,它返回一个布尔值,并在当前打开的工作簿(Workbooks
集合)中循环检查名称,使用如下代码:
foreach (_Workbook wb in xlApp.Workbooks)
{
Console.WriteLine(wb.Name);
}
如果工作簿已保存,则不需要workbook.Close()
,这反映了Excel的正常行为。但是,需要释放所有Excel对象引用。正如您所发现的,这有点麻烦,Close
和Quit
并不能单独实现这一点。
static bool IsOpen(string book)
{
foreach (_Workbook wb in xlApp.Workbooks)
{
if (wb.Name.Contains(book))
{
return true;
}
}
return false;
}