2016-04-12 41 views
0

8個月前我曾經建議成立臨時表中,然後推到正式表格,防止重複條目,每這篇文章:Best way to prevent duplicate data on copy csv postgresqlPostgreSQL的插入停止工作,重複鍵值違反

它一直工作非常好,但今天我注意到了數據中的一些錯誤和差距。

這裏是我的插入語句: insert statement

而這裏的指數是如何設置的: indexes

而這裏的我得到了錯誤的例子,雖然在下代下插入,它經歷了。 error

這是它經歷罰款: success

我沒有注意到,在數據輸入的任何大的變化。以下是現在的數據: data looks like 總之,我已經注意到插入語句最近的不同之處,並且成功是不穩定​​的,導致數據庫中存在很大的數據差距。感謝您的幫助,我很樂意提供更多詳細信息,但我想知道我的信息是否聽起來像其他人已經處理的內容。

非常感謝您的幫助, 小號

+0

文本的發佈的屏幕截圖是不是一個好主意,爲什麼不發佈文字本身? –

+0

我想我可能會被問到。因爲我爲數據庫使用了遠程桌面連接,並且在嘗試複製/粘貼時最好不過了。另外,我認爲這是一個概念性問題,而讀者則試圖重新創建代碼並對其進行測試。 – user1610717

+0

請檢查列''時間''是否有'null'值。 '空'值突破'不在'比較 –

回答

0

戈登在his answer to your previous question指出的那樣,如果你要獨佔訪問表這種方法只適用。存在檢查與插入本身之間存在延遲,並且如果另一個進程在此窗口期間修改了表,則最終可能會出現重複項。

如果您使用的是Postgres 9.5+,最好的方法是跳過存在檢查並簡單地使用INSERT ... ON CONFLICT DO NOTHING聲明。

在較早的版本中,最簡單的解決方案(如果您可以負擔得起)將在導入期間輸入lock the table。否則,你可以模擬ON CONFLICT DO NOTHING(雖然效率較低)使用循環和異常處理程序:

DO $$ 
DECLARE r RECORD; 
BEGIN 
    FOR r IN (SELECT * FROM holding) LOOP 
    BEGIN 
     INSERT INTO ltg_data (pulsecount, intensity, time, lon, lat, ltg_geom) 
     VALUES (r.pulsecount, r.intensity, r.time, r.lon, r.lat, r.ltg_geom); 
    EXCEPTION WHEN unique_violation THEN 
    END; 
    END LOOP; 
END 
$$ 

順便說一句,DELETE FROM holding是耗時的,可能是不必要的。創建登臺表TEMP,它將在會話結束時自動清除。您可以輕鬆地建立其結構相匹配的導入目標的表格:

CREATE TEMP TABLE holding (LIKE ltg_data); 
+0

非常感謝這些想法!我確實擁有對桌子的獨家使用權。只有在插入腳本運行時每10分鐘纔會修改一次。我有時會訪問表格來查看數據。 所以,我應該仍然嘗試「插入......衝突什麼都不做」聲明?如果「衝突中」部分替換了我原來插入語句的「哪裏」部分? 現在你知道我們擁有獨家使用權嗎?另外,這是一個7mil的排桌子。不知道這個尺寸是否影響任何東西。 – user1610717

+0

當您重新運行它時,它的工作原理表明該表的狀態已更改;如果沒有其他作者參與,我不確定這會如何發生。進口需要多長時間?任何cron作業重疊的機會?如果不是這樣,[語句記錄](http://blog.endpoint.com/2012/06/logstatement-postgres-all-full-logging.html)可能會提供一些見解。重新考慮ON CONFLICT條款,不管你當前的問題,這可能是一個更好的方法,是的,它會代替現有的WHERE條款。 –

相關問題