2009-08-19 65 views
1

作爲一種粗略的猜測優化方法,我工作中的開瓶器(幾年前)將我們的comments表中的body列移至次表comment_extensions表中。每次我們想要顯示評論時,加入一個加入似乎都不明智,所以我會嘗試將該列移回到我們的comments表中並運行一些基準測試。PostgreSQL:什麼是更新3m記錄的有效方法?

我的問題是此更新抓取。我讓它跑了一個小時,然後關掉它,擔心這會花一整晚。

UPDATE comments SET body = comment_extensions.body 
       FROM comment_extensions 
       WHERE comments.id = comment_extensions.comment_id; 

這是一個PostgreSQL 8.1數據庫,並且comment_extensions.comment_id被索引。

任何建議讓這個運行更快?

回答

2

這個怎麼樣?

http://www.postgresql.org/docs/8.1/interactive/sql-createtableas.html

CREATE TABLE joined_comments 
    AS SELECT c.id, c.author, c.blablabla, ce.body 
    FROM comments c LEFT JOIN comment_extensions ce 
    ON c.id = ce.comment_id; 

這將創建一個新的joined_comments表。這可能已經足夠了(你需要重新創建索引等),但我記得Postgres 8.1有一個關於串行列創建方式的問題(抱歉找不到鏈接)。

所以我的建議是,你有這個新的聯接表後,你複製到來自該joined_comments表的二進制文件,創建一個新的評論表,說明該ID是從一開始的序列權利,然後從該COPY BINARY文件添加到新評論表中。然後,重新創建索引。

2

那麼,對於學術問題,爲什麼這是不明智的?查找的百分比涉及需要知道評論信息?

我的建議:小批量更新(每次10,000行?)。它可能還需要一整晚。根據系統的性質,您可能還必須實施切換邏輯,以防止系統在此遷移過程中更新或從您的擴展表中拔出。

大型數據庫像這樣受傷;)

+0

每當我們顯示評論時,我們都需要在評論文本的'comment_extensions'表中對應的記錄。所以這是100%的時間。似乎沒有必要在兩張桌子上應該有一張桌子。 感謝您對小批量的建議。如果我們這樣做的話,我們可以在遷移過程中保持網站的流暢。 – user57995 2009-08-19 18:15:16

+0

是的,這聽起來像一個負面的「優化」。檢查主表中的註釋字段。如果主表的註釋爲空,請在擴展表中檢查註釋。將所有新註釋插入主表中。這將保持你的網站,直到你準備好轉儲擴展表。小批量更新(取決於您的站點的負載,10k可能太多)會讓系統在後臺進行遷移時執行其生產工作。 – 2009-08-19 20:01:36

1

在執行此操作時禁用日誌可能會使您受益匪淺。如果它是非生產表中的測試,那麼您可能不需要日誌文件爲您提供的保護。

如果comments.body上有一個索引或關鍵字,則在更新之前將其刪除並在之後重新創建。

是comments.body字段固定寬度字符(N)還是它是一個varchar? Varchar過去比char()慢,我懷疑它仍然是。所以使用char not varchar。

如果您選擇將數據合併到數據文件(例如引用的csv)並編寫腳本將其轉換爲INSERTS,然後清空註釋表並使用插入可能比查詢更快的INSERTS加載它你有,儘管comments.id上的索引正在幫助速度。

無論如何,3e6記錄都需要一些時間。

相關問題