ไม่มีORDER BY
ในSQL UPDATE
คำสั่ง Postgres อัปเดตแถวตามลำดับโดยพลการ:
เพื่อหลีกเลี่ยงการหยุดชะงักด้วยความมั่นใจแน่นอนคุณสามารถเรียกใช้คำสั่งของคุณในการแยกการทำธุรกรรมแบบอนุกรมได้ แต่มันมีราคาแพงกว่าและคุณต้องเตรียมคำสั่งซ้ำในความล้มเหลวของการทำให้เป็นอนุกรม
แนวทางปฏิบัติที่ดีที่สุดของคุณน่าจะล็อคอย่างชัดเจนด้วยSELECT ... ORDER BY ... FOR UPDATE
ในแบบสอบถามย่อยหรือแบบสแตนด์อโลนSELECT
ในการทำธุรกรรม - ในระดับเริ่มต้นแยก "read มุ่งมั่น" การอ้างอิง Tom Lane บน pgsql-general :
ควรเป็นเรื่องถูกต้อง --- การล็อก FOR UPDATE เป็นขั้นตอนสุดท้ายเสมอในขั้นตอนการเลือก
สิ่งนี้ควรทำงาน:
BEGIN;
SELECT 1
FROM foo
WHERE baz = 1234
ORDER BY bar
FOR UPDATE;
UPDATE foo
SET bar = bar + 1
WHERE baz = 1234;
COMMIT;
ดัชนีหลายคอลัมน์ใน(baz, bar)
อาจเหมาะสำหรับประสิทธิภาพ แต่เนื่องจากbar
มีการปรับปรุงจำนวนมากอย่างชัดเจนดัชนีคอลัมน์เดี่ยว(baz)
อาจจะดีกว่า ขึ้นอยู่กับปัจจัยสองประการ วิธีการหลายแถวต่อbaz
? มีการปรับปรุง HOTได้โดยไม่ต้องดัชนีหลายคอลัมน์หรือไม่ ...
หาก baz
มีการอัปเดตพร้อมกันก็ยังมีโอกาสที่มุมกรณีที่ไม่น่าเป็นไปได้สำหรับความขัดแย้ง(ตามเอกสารประกอบ) :
เป็นไปได้สำหรับSELECT
คำสั่งที่รันที่READ COMMITTED
ระดับการแยกธุรกรรมและการใช้ORDER BY
และส่วนคำสั่งล็อกเพื่อส่งคืนแถวตามลำดับ ...
นอกจากนี้หากคุณควรมีข้อ จำกัด เฉพาะที่เกี่ยวข้องbar
ให้พิจารณาDEFERRABLE
ข้อ จำกัดเพื่อหลีกเลี่ยงการละเมิดที่ไม่ซ้ำกันภายในคำสั่งเดียวกัน คำตอบที่เกี่ยวข้อง:
CREATE TABLE
รหัส