在C#中运行程序后如何释放内存?

我有一个C#程序,我从Excel文件中读取数据,其中包含大约40000个数字。 这是我的代码的一部分:

Microsoft.Office.Interop.Excel.Application _excelApp = new Microsoft.Office.Interop.Excel.Application(); _excelApp.Visible = true; string fileName = "D:\\data.xlsx"; Workbook workbook = _excelApp.Workbooks.Open(fileName, Type.Missing); Worksheet worksheet = (Worksheet)workbook.Worksheets[1]; Range excelRange = worksheet.UsedRange; Object[,] valueArray = (object[,])excelRange.get_Value(XlRangeValueDataType.xlRangeValueDefault); int num = worksheet.UsedRange.Rows.Count; workbook.Close(false, Type.Missing); _excelApp.Quit(); for (int row = 1; row <= num; ++row) { data1.Add(Convert.ToDouble(valueArray[row, 1])); data2.Add(Convert.ToDouble(valueArray[row, 2])); } 

每次运行程序时,excel文件都会显示一会儿并closures。 但是在windows的后台进程中有一些打开的excel文件,并且消耗ram,降低windows的速度。 我怎样才能完全closuresexcel文件,并退出我的代码中的内存?

谢谢。

您需要释放您使用的COM对象,以便它们可以正确closures。

试试这个代码:

 var _excelApp = new Microsoft.Office.Interop.Excel.Application(); _excelApp.Visible = true; var fileName = "D:\\data.xlsx"; var workbooks = _excelApp.Workbooks; var workbook = workbooks.Open(fileName, Type.Missing); var worksheet = (Worksheet)workbook.Worksheets[1]; var excelRange = worksheet.UsedRange; Object[,] valueArray = (object[,])excelRange.get_Value(XlRangeValueDataType.xlRangeValueDefault); int num = worksheet.UsedRange.Rows.Count; Marshal.FinalReleaseComObject(excelRange); Marshal.FinalReleaseComObject(worksheet); workbook.Close(false, Type.Missing); Marshal.FinalReleaseComObject(workbook); Marshal.FinalReleaseComObject(workbooks); _excelApp.Quit(); Marshal.FinalReleaseComObject(_excelApp); for (int row = 1; row <= num; ++row) { data1.Add(Convert.ToDouble(valueArray[row, 1])); data2.Add(Convert.ToDouble(valueArray[row, 2])); } 

我没有testing过这个代码,但它应该是接近的。

请注意,你绝对要做这样的代码:

 var workbooks = _excelApp.Workbooks; var workbook = workbooks.Open(fileName, Type.Missing); 

…你不能这样做:

 var workbook = _excelApp.Workbooks.Open(fileName, Type.Missing); 

…因为这留下_excelApp.Workbooks中间对象无法释放。

你想强制垃圾收集器调用,这基本上通过调用GC.Collect()来实现。

当您调用GC.Collect时,GC将在一个单独的线程上运行每个对象的终结器。 因此,另一种记住的方法是GC.WaitForPendingFinalizers。 这个同步方法直到GC.Collect完成工作后才会返回。

例:

 public void MethodUsingTonsOfMemory(){ // do memory intensive stuff GC.Collect(); GC.WaitForPendingFinalizers(); // wait for memory to be released Debug.WriteLine("Memory should be clear now"); }