2011-02-11 76 views
6

爲什麼這行代碼導致Excel不能退出?爲什麼此代碼導致Excel無法正常關閉?

Excel.Range range = (Excel.Range)ws.Cells[1,1]; 

如果是因爲鑄造,那麼這個代碼是不是會導致同樣的問題?

Excel.Worksheet ws = (Excel.Worksheet)wb.ActiveSheet; 

我試過了。但是,這工作。 Excel將關閉。

如果我使用這段代碼。 Excel關閉。

Excel.Range range = ws.get_Range("A1","A1"); 

那麼有什麼區別?是的,我知道有一百萬的「如何正確關閉Excel」線程。但既然這是一個問題,而不是一個答案,我決定問一個新問題,而不是在其他人的問題中提問。

這是我的代碼。但當然還有其他代碼。我只是評論一切,並慢慢嘗試哪些行導致Excel不關閉。我意識到即使沒有使用垃圾收集器,Excel仍然會關閉。我不想用大錘關閉Excel。

謝謝。

Excel.Application objExcel = new Excel.Application(); 
Excel.Workbooks wbs = objExcel.Workbooks; 
Excel.Workbook wb = wbs.Open(saveFileDialog1.FileName, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing); 
Excel.Worksheet ws = (Excel.Worksheet)wb.ActiveSheet; 
//Excel.Range range = (Excel.Range)ws.Cells[1,1]; 
Excel.Range range = ws.get_Range("A1","A1"); 

FinalReleaseAnyComObject(range); 
FinalReleaseAnyComObject(ws); 
wb.Close(Type.Missing, Type.Missing, Type.Missing); 
FinalReleaseAnyComObject(wb); 
FinalReleaseAnyComObject(wbs); 
objExcel.Quit(); 
FinalReleaseAnyComObject(objExcel); 

目前我試過,直到objExcel,wbs,wb和ws。這4個對象不會造成問題。

private static void FinalReleaseAnyComObject(object o) 
{ 
    Marshal.FinalReleaseComObject(o); 
    o = null; 
} 

我意識到你不能重複使用這個變量。

Excel.Range range = ws.get_Range("A1","G1"); 
range = ws.get_Range("A1", "A1"); 

這將導致Excel不能正常關閉。相反,使用這個。

Excel.Range range = ws.get_Range("A1","G1"); 
FinalReleaseAnyComObject(range); 
range = ws.get_Range("A1", "A1"); 
+0

@user:靠近,你的意思是崩潰?看來演員操作不應該故意關閉Excel。 –

+0

@ p.campbell關閉,我的意思是正確關閉Excel。 Excel或COM對象有一個衆所周知的問題,不正確關閉。即使在我調用objExcel.quit()之後,Excel進程仍將保留在任務管理器中。 – user607455

回答

11

有一個隱藏的Range接口指針,您看不到,Cells屬性返回它。然後,將索引器表達式應用於該表達式,並取消引用該範圍的默認Item屬性。獲得另一個範圍。

這就是爲什麼嘗試自己管理COM接口指針是一個糟糕的主意。相信垃圾收集器到總是說得對。 GC.Collect()和GC.WaitForPendingFinalizers()如果你真的想真正地按需要退出。請務必閱讀this answer以瞭解爲什麼在調試程序時,這並不總是按預期工作。

+0

我聽說垃圾收集器很貴?因爲我沒有讀過它,所以不太確定。 – user607455

+0

剛試過這個「Excel.Range range =(Excel.Range)ws.Cells [1,1];」與垃圾收集器,它的工作原理!那哪個更好?單元格或get_Range?我應該完全避免GC嗎? – user607455

+0

美麗的解釋漢斯。 user607455,不,漢斯說在清理COM對象時必須使用GC。沒有避免它。看到這裏的更詳細的討論:http://stackoverflow.com/questions/158706/how-to-properly-clean-up-excel-interop-objects-in-c/159419#159419 –

相關問題