2011-12-27 80 views
2

我們有一個打開模板excel文件,寫入數據行的自動處理,並將該文件返回給用戶。這個過程通常很快,但是最近我被要求用一些Excel公式添加一個摘要頁面到其中一個模板,現在這個過程需要一段時間。寫入包含公式的Excel文件非常慢

它成功地用了幾分鐘後約5個記錄上運行,但是這周的記錄集幾乎是400行,我已經讓它運行時間最長的是約一個半小時,再取消。如果沒有這些公式,只需要幾秒鐘就可以運行。

是否有任何已知問題與行寫入包含公式的Excel文件?或者有沒有辦法告訴Excel不要評估公式,直到文件被用戶打開?

對彙總表上的公式是這些:

' Returns count of cells in column where data = Y 
=COUNTIF(Sheet1!J15:Sheet1!J10000, "Y") 
=COUNTIF(Sheet1!F15:Sheet1!F10000, "Y") 

' Return sum of column where data is a number greater than 0 
' Column contains formula calculating the difference in months between two dates 
=SUMIF(Sheet1!I15:Sheet1!I10000,">0",Sheet1!I15:Sheet1!I10000) 

' Returns a count of distinct values in a column 
=SUMPRODUCT((Sheet1!D15:Sheet1!D10000<>"")/COUNTIF(Sheet1!D15:Sheet1!D10000,Sheet1!D15:Sheet1!D10000&"")) 

並寫入到Excel的代碼看起來是這樣的:

已經救了我多年來
Dim xls as New Excel.Application() 
Dim xlsBooks as Excel.Workbooks, xlsBook as Excel.Workbook 
Dim xlsSheets as Excel.Sheets, xlsSheet as Excel.Worksheet 
Dim xlsCells as Excel.Range 

xls.Visible = False 
xls.DisplayAlerts = False 

xlsBooks = xls.Workbooks 

xlsBooks.Open(templateFile) 
xlsBook = xlsBooks.Item(1) 

' Loop through excel Sheets. Some templates have multiple sheets. 
For Each drSheet as DataRow in dtSheets.Rows 
    xlsSheets = xlsBook.Worksheets 
    xlsSheet = CType(xlsSheets.Item(drSheet("SheetName")), Excel.Worksheet) 
    xlsCells = xlsSheet.Cells 

    ' Loop though Column list from Database. Each Template requires different columns 
    For Each drDataCols as DataRow in dtDataCols.Rows 

     ' Loop though Rows to get data 
     For Each drData as DataRow in dtData.Rows 
      xlsCells(drSheet("StartRow") + dtData.Rows.IndexOf(drData), drDataCols("DataColumn")) = drData("Col" + drDataCols("DataColumn").toString).toString 
     Next 
    Next 
Next 

xlsSheet.SaveAs(newFile) 
xlsBook.Close 
xls.Quit() 
+1

嘗試設置**手動**計算模式。 - http://msdn.microsoft.com/en-us/library/bb687891.aspx – adatapost 2011-12-27 14:24:49

+1

@AVD這工作,謝謝:)如果您發佈,作爲一個答案我會接受它 – Rachel 2011-12-27 14:56:45

+0

高興你得到它的工作。 – adatapost 2011-12-27 15:05:22

回答

1

隨着auto模式計算,之後每數據輸入/改變發生重新計算。我有同樣的問題,通過設置Manual計算模式解決。 (參考MSDN link。)

xls.Calculation = Excel.XlCalculation.xlCalculationManual 

而且,這個屬性只能一個工作簿已經打開,否則會引發一個運行時錯誤後進行設置。

+1

謝謝。我更新了您的答案,以包含代碼示例以及僅在打開工作簿後設置它的說明。 – Rachel 2011-12-27 15:11:32

0

一種方法是添加

Application.ScreenUpdating = False 

直接執行一個潛在的冗長的方法,然後

Application.ScreenUpdating = True 

直接在代碼之後,或者至少在某些稍後的時間點。這迫使Excel不在可見屏幕上重繪任何東西,直到完成爲止這個問題是我發現冗長的運行操作經常出現的地方。

+0

Excel不會在屏幕上繪製任何東西。該文件構建在Web服務器上,然後保存並返回給用戶進行下載。 – Rachel 2011-12-27 14:48:53

3

你寫一個小區的Excel重新計算打開的工作簿,並刷新屏幕每次。這兩件事情都很慢,所以你需要設置Application.Screenupdating = false和Application.Calculation = xlCalculationManual

此外,每次寫入單元時都會有很高的開銷,所以要快速地將數據,然後通過一次調用Excel對象模型將數組寫入範圍。

+0

我試着設置'Application.Calculation',但是我得到一個運行時錯誤(認爲它是'HRESULT:0x800A03EC')。我也嘗試設置'Application.ScreenUpdating',這沒有什麼區別。我無法寫入一組連續的單元格,因爲有時模板將自己的列與彙總數據的數據列混合在一起,而且我無法修改模板。 「 – Rachel 2011-12-27 14:53:18

+1

+1」用於「在陣列中累積數據的速度快得多,然後將數組寫入範圍」 – phoog 2011-12-27 15:03:18

+0

+1。這是一個很好的答案,但AVD首先回答瞭解決問題的解決方案,因此我接受了他的回答。 – Rachel 2011-12-27 15:13:38

相關問題