2016-04-19 82 views
0

使用Excel VBA清理大型csv文件。爲此,我將csv文件加載到訪問數據庫中,然後使用sql查詢執行所有數據轉換活動。因此,抽象過程如下Excel -Access DB -ADO。內存泄漏 - >超出系統資源

打開Excel - >開始單擊打包訪問數據庫 - >將csv文件加載到不同的表 - >使用adoddb連接執行不同的DDl以及數據庫上的DML語句 - >輸出最終數據。

我在這裏面臨的問題是內存使用總是由excel增加。它似乎訪問數據庫處理也添加到Excel本身。所以最終我得到了錯誤"System Resource Exceeded"

每次執行查詢時。內存使用率高漲並永遠不會下降。這些查詢在3-4個表中大約有10k到10萬條記錄。

爲什麼內存使用永遠不會下降?

每當我做一個ddl/dml查詢我打開adodb連接並關閉它。我使用後關閉所有記錄集並設置爲無。但內存使用率始終沒有下降。

看到有關的不同文章。但大多數人都在討論關於同一個excel文件中的數據。在我的情況下,沒有數據保存在內存或Excel文件中。

我在微軟這裏看到一篇文章,裏面講到了excel本身的數據。 https://support.microsoft.com/en-us/kb/319998

有沒有人知道這個請求的任何解決方法?

對於例如:將數據加載到從csv文件表我用下面的代碼

StrSql = "SELECT * into " & TableName & " FROM [Text;FMT=Delimited;HDR=YES;DATABASE=" & DSPath & "].[" & DSName & "]" 
    ExecuteSQL StrSql 


Private Function ExecuteSQL(Sql As String) As Long 
    Dim Con As ADODB.Connection 
    Dim I As Long 

    Connect Con 
    Con.Execute Sql, I 
    ExecuteSQL = I 
    CloseCon Con 
End Function 

Public Sub CloseCon(ByRef Con As ADODB.Connection) 
    If Not Con Is Nothing Then 
    If Con.State = adStateOpen Then 
     Con.Close 
     Set Con = Nothing 
    End If 
    End If 
End Sub 

Public Sub Connect(ByRef Con As ADODB.Connection) 
Dim ConStr As String 

If Not Con Is Nothing Then 
    If Con.State = adStateOpen Then 
     Exit Sub 
    End If 
End If 
On Error GoTo err 
    CloseCon Con 
    Set Con = New ADODB.Connection 
    ConStr = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & DBFile & ";Persist Security Info=False" 
    Con.Open ConStr, , , -1 
    Exit Sub 
err: 
End Sub 

這有助於一點點。

而不是每次打開和關閉使用一個單獨的連接對象我試圖使用一個公開的連接對象,它是從開始打開,只有當過程完成時關閉。通過這種方式,內存消耗減少,並且進程運行更多時間。

+1

爲什麼不直接在Access中執行所有操作?似乎沒有必要從Excel去操縱Access。 –

+0

我們沒有安裝訪問界面。只需使用噴氣發動機。所以用戶可以打開Excel工具並提供輸入。 – kten

+0

你可以發佈代碼嗎? –

回答

1

您的代碼看起來很健全。問題是在參考確認微軟:「由ADO查詢使用的內存無法通過關閉被回收和釋放ADO對象來釋放內存的唯一方法是退出Excel

所以我們。現在必須退出Excel,然後回收資源。

  1. 「退出Excel」意味着從您正在使用當前工作簿必須被關閉,或者

  2. 「退出Excel」意味着要辭去所有實例的Excel,因此Excel可以有效地從內存中刪除。

Ad。 1:在這種情況下,您可以創建一個「父工作簿」來啓動另一個包含ADODB處理一部分的工作簿。它在部分處理後退出,並且父母啓動一個新的其他工作簿,繼續處理等。使用一些智能切割&粘貼來調整何時退出每個工作簿。

廣告2:在這種情況下,您可以使用例如Word啓動Excel.Application的一個新實例,並按照與1相同的方式繼續。只是希望MS-Office不那麼集成,以便在任何Office程序運行時ADO DLL不會退出...

當然,向微軟證實抱怨你的IT部門安裝Access UI的bug可能會更好。

+0

嗯是的它是有道理的。即使它涉及相當數量的開銷。它看起來沒有其他解決方法。無論如何,我發現連續開放和關閉連接的一個部分問題,我在問題本身發佈 – kten