2012-12-10 12 views
0

我有一個數據庫,這不是很快,我有一個大的CSV約65000行。我需要交叉檢查這些是否存在,並在需要時更新數據庫。C#crosscheck緩慢的數據庫與大型CSV

  • 在CSV中,有一列包含數據庫ID。它總是1:1的關係。
  • CSV可能會爲數據庫保存新的輸入,因此可能會發生沒有數據庫條目的情況。
  • 我無法遍歷CSV並檢查每一行,因爲它太慢了。
  • 首先獲取數據庫中的所有結果並將它們存儲爲每次循環都不起作用,因爲這會拉出大量的RAM。

我怎樣才能做到以下幾點:

  • 檢查的CSV行有一個數據庫條目。如果是,請將其寫入另一個CSV文件。
  • 如果該行沒有數據庫條目,則將其寫入其他文件。
  • 保持5分鐘內的時間跨度,最好更短。

CSV有很多列(例如70),但我只需要列5來交叉檢查ID。我試圖先循環訪問CSV文件,然後用數據庫檢查它,但這太慢了。它可能需要10多分鐘。我也嘗試從數據庫中獲取所有條目,並循環訪問這些條目。隨着循環,運行CSV(使用BufferedStream),並檢查它。這會顯着減少時間(最多5分鐘),但無法記錄數據庫中不存在的條目。

有什麼辦法可以在保持加速的同時做到這一點?

+0

它是什麼樣的數據庫?如果它是一個關係數據庫,並且數據庫上的索引設置正確,那麼表中的id的select/update應該很快。 –

+0

你對CSV有什麼控制權?你能刪除出現在數據庫中的記錄嗎? 數據庫ID的列是否遵循您可以利用的約定來節省時間?例如你能刪除所有的ID小於你添加到數據庫中的最後一個ID嗎? – Rawrgramming

+0

@JohnKoerner這不是我的數據庫,我不能編輯它。它對我來說是隻讀的。我想這些指標並不是很好,或者根本沒有。我必須通過ODBC連接器進行連接。 –

回答

0

最新回答,但我已經解決了這個問題:我正在將我需要的CSV列拖入DataTable。然後,我獲取需要檢查的所有行(它有一定數量,我可以過濾),然後遍歷這些數據庫行。每行將檢查DataTable中的相應ID並將數據置於新的CSV中。之後,DataTable中的行將被刪除。最後,我有一個CSV,其中存在的行將被導入到系統中,還有一個DataTable將被導出到CSV,其中包含需要添加的行。

感謝Gregory幫助我走上正軌。

1

沒有足夠的信息給你一個適當的分析,並最終解決問題的鐵包裝解決方案。我可以提出一些建議。爲了記錄,具有65,000條記錄的CSV並不是那麼龐大。我也不同意漫步文件的速度太慢,因爲我親自研究過使用流讀取器比較大小爲GB的文件,該文件的可能性要大一個數量級。

首先,你可以考慮把這個問題放在頭上。在運行CSV時,不要拉動數據庫,而應考慮將整個集合拉到內存中(如果您有一個龐大的數據庫,這不是一個好主意,但是如果它是可管理的,則是一個選項)。如果有點大,你甚至可以寫出數據庫(假設這是一個表或視圖(或查詢可能是一個視圖))到另一個CSV。這裏的核心重點是讓慢數據庫脫離循環。注意:如果這是一個高度事務性的系統,並且您需要「最新的(或5分鐘)準確快照」,這可能是不夠的。我發現這是一種不切實際的期望(儘管進行了大量編輯,數據現在仍然代表5分鐘前)。

接下來,您可以考慮減少設置。在您的問題中已經提到的簡單方法是將工作CSV從70列減少到您需要的5列。如果您從數據庫中提取相同的數據進行比較,情況也會如此。這隻有在加載時間成爲瓶頸時纔有效。根據你的描述,我嚴重懷疑是這種情況。

您也可以考慮將兩位數據存入內存並在那裏計算。非常快。如果由於大小而無法將兩個項目比較到內存中,這將不起作用,這就是爲什麼要篩選到需要的列是一個有用的練習。

由於您提到數據庫ID,聽起來像CSV檢查多個數據庫。考慮首先通過數據庫ID排序CSV。如前所述,排序算法速度非常快,應該能夠在幾秒鐘內對65,000條記錄進行排序。排序的瓶頸通常是內存數量和I/O速度(主要是磁盤速度)。然後您可以攻擊每個數據庫。

正如我在開始時所說的,我只有足夠的信息給出提示,而不是實際的解決方案,但希望這刺激了一些想法。

+0

它只有1個數據庫,對不起,如果我不清楚這一點。數據庫應該保持相同數量的行,因爲文件應該只更新/添加。是65k或最終100k行大到拉回到內存,或任何計算機可以處理好嗎? –

+0

另外,您需要提供哪些其他信息才能進行正確的分析? –