[英]Curious behaviour with ExecuteBatch and Prepared Statements
我有一個奇怪的問題,涉及同時使用JDBC將executeBatch和Prepared Statements放置到PostgSQL數據庫中的大量數據。 我正在使用executeBatch每次向數據庫發送50,000條語句。
我知道執行批處理和准備好的語句正在工作; 一些數據正在進入數據庫。 准備好的語句是
INSERT INTO time ( time_id, log_id, phenomenon_time, qc_phenomenon_time )
SELECT nextval( 'time_seq' ), ?, ?, ?
並將其與execute batch一起使用,可以在數據庫中找到數據。
使用以下准備好的語句時,
INSERT INTO result_3d ( result_3d_id, time_id, variable_id, value, qc_value )
SELECT nextval( 'result_3d_seq' ), ( SELECT t.time_id
FROM time t
WHERE t.log_id = ?
AND t.phenomenon_time = ? ), ?, ?, ?
執行批處理時,數據庫中沒有數據。 我什至沒有打開數據庫日志記錄,第一次發現了所有內容,而第二次卻什么也沒有。 第二條准備好的語句依賴於第一條語句的數據,但數據庫甚至看不到第二條語句。
沒有異常被拋出。 唯一奇怪的是,對於第二條准備好的語句,返回的數組的大小為零。 批處理批次立即返回。 第二條准備好的語句中的子查詢是否被允許?
我使用postgres-9.1-901.jdbc4.jar作為針對PostgreSQL v8.3.19數據庫的JDBC驅動程序。
請幫忙。
我不知道JDBC驅動程序,但是您使用9.1版並連接到過時的PostgreSQL 8.3.19看起來很可疑。 將PostgreSQL升級到9.1可能會解決您的問題。
通常,如果您已將time.time_id
和result_3d.result_3d_id
列定義為serial
列(可能應該如此),或者已將這些列的DEFAULT值手動設置為各自序列上的nextval()
,則不需要從序列中獲取id。 值將自動填寫 。
第二條准備好的語句中的子查詢是否被允許?
是的,原則上是。 但是它可能永遠不會返回超過一行 。 您必須保證(t.log_id, t.phenomenon_time)
唯一性或添加LIMIT 1
:
(SELECT t.time_id
FROM time t
WHERE t.log_id = ?
AND t.phenomenon_time = ?
LIMIT 1)
使用PostgreSQL 9.1時,您可以將兩個INSERT
命令與一個可修改數據的CTE鏈接在一起,這應該會更快一些,並且避免了以子查詢開頭的需求:
WITH data (log_id, phenomenon_time, qc_phenomenon_time
,variable_id, value, qc_value ) AS (
VALUES(?, ?, ?, ?, ?, ?) -- cast to appropriate types!
)
, i AS (
INSERT INTO time (log_id, phenomenon_time, qc_phenomenon_time)
SELECT log_id, phenomenon_time, qc_phenomenon_time
FROM data
RETURNING time_id, log_id, phenomenon_time
)
INSERT INTO result_3d (time_id, variable_id, value, qc_value)
SELECT i.time_id, d.variable_id, d.value, d.qc_value
FROM data d
JOIN i USING (log_id, phenomenon_time);
所有這一切可能會或可能不會解決潛在的問題,但是很有可能會解決。
我的第一個想法是潛在的問題可能是並發問題-意味着在提交第一個INSERT
之前啟動了第二個INSERT
。 但是,如果數據庫甚至看不到第二個調用,則這里還有其他工作。
我要回答自己的問題,因為我描述的症狀與“執行批處理”或“准備好的語句”無關。 在進行一些重構時,我沒有發表重要的聲明。
this.preparedStatement.addBatch();
所以這是我的壞事。 這些症狀用缺少的語句很好地描述了代碼的行為。
感謝您的意見。 有些給了我新的學習領域。 謝謝歐文。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.