คำสั่งเดียวเช่นนั้นที่ทำงานได้เหมือนกันกับ MyISAM หรือ InnoDB กับธุรกรรมหรือกับ autocommit = ON มันบล็อกเพียงพอที่จะทำแบบสอบถามจึงบล็อกการเชื่อมต่ออื่น ๆ เมื่อเสร็จสิ้นการเชื่อมต่ออื่น ๆ จะดำเนินต่อไป ในทุกกรณีคอลัมน์จะลดลงทันที 11
ผู้ใช้รายที่สามอาจเห็นค่าที่ลดลงโดย 0 หรือ 4 หรือ 7 หรือ 11 "เวลาที่แน่นอนมาก" เป็นไปไม่ได้เพราะในบางครั้งในการดำเนินการของแต่ละคำสั่งล็อคแบบเธรดเดียวจะถูกตรวจสอบ / ตั้งค่า / อะไรก็ตาม . นั่นคือพวกเขาจะได้รับการต่อเนื่องอย่างรวดเร็วจนคุณมองไม่เห็น
InnoDB ล็อคเฉพาะแถวไม่ใช่ตาราง (ตกลงคำสั่ง DDL ทำการล็อคที่โดดเด่นยิ่งขึ้น)
สิ่งที่น่าสนใจยิ่งกว่าคือธุรกรรมที่ปรับเปลี่ยนสองสิ่งหรือใช้เวลาในการสังเกต:
กรณีความตั้งใจ:รายการเดียว แต่สละเวลา:
BEGIN;
SELECT something;
think about it for a while
UPDATE that something;
COMMIT;
การเลือกจะต้องมีการเขียนดังนี้:
SELECT something FOR UPDATE;
สิ่งนี้จะบอกการเชื่อมต่ออื่น ๆ "ฉันต้องการอัพเดทแถวโปรดอย่าทำให้ฉันสับสน" (ฉันขอยกตัวอย่างนี้เพราะมือใหม่จำนวนมากพลาดความฉลาดนี้)
กรณีการหยุดชะงัก: ล้อเล่นกับ 2 สิ่ง:
BEGIN; -- in one connection
UPDATE thing_1;
UPDATE thing_2;
COMMIT;
BEGIN; -- in another connection, at the "exact same time"
UPDATE thing_2;
UPDATE thing_1;
COMMIT;
นี่คือตัวอย่างคลาสสิกของการหยุดชะงัก - แต่ละคว้าสิ่งหนึ่งแล้วเอื้อมมือเพื่อสิ่งอื่น เห็นได้ชัดว่าไม่สามารถทำงานได้ ธุรกรรมหนึ่งถูกฆ่า อื่น ๆ เสร็จสมบูรณ์ ดังนั้นคุณต้องตรวจสอบข้อผิดพลาดเพื่อให้คุณสามารถค้นพบได้
ปฏิกิริยาปกติต่อการหยุดชะงักคือการเล่นซ้ำธุรกรรมทั้งหมดที่ล้มเหลว จากนั้นการเชื่อมต่ออื่น ๆ จะไม่รบกวนและควรดำเนินการต่อโดยไม่มีปัญหา (ตกลงการเชื่อมต่ออื่นสามารถสร้างการหยุดชะงักได้อีก)
กรณีที่ล่าช้า:หากการเชื่อมต่อทั้งสองหยิบหลายสิ่งในลำดับเดียวกันการเชื่อมต่อหนึ่งอาจล่าช้าจนกว่าการเชื่อมต่ออื่น ๆ จะเสร็จสิ้น เพื่อให้นี้จาก "รอตลอดไป" มีการเริ่มต้น innodb_lock_wait_timeout
50 คู่ที่เรียบง่ายของคุณUPDATEs
เป็นตัวอย่างของกรณีนี้จริง ๆ หนึ่งจะจบทันที อีกจนจนครบเป็นครั้งแรก
สังเกตว่า Deadlock สามารถเปลี่ยนเป็น Delay ได้อย่างไรโดยการสั่งซื้อสิ่งที่คุณสัมผัสอย่างสม่ำเสมอ
autocommit = 1: ด้วยการตั้งค่านี้และไม่มีการเรียกBEGIN
แต่ละคำสั่งจะมีประสิทธิภาพ:
BEGIN;
your statement
COMMIT;
autocommit = 0: นี่เป็นปัญหาที่รอให้เกิดขึ้น เมื่อคุณดำเนินการแบบสอบถามการเขียนBEGIN
จะถูกสร้างขึ้นโดยปริยาย COMMIT
แต่ก็เป็นความรับผิดชอบของคุณกับปัญหาในที่สุด หากคุณไม่ทำเช่นนั้นคุณจะสงสัยว่าทำไมระบบของคุณถึงหยุดทำงาน (ข้อผิดพลาด newbie ทั่วไปอื่น ๆ ) คำแนะนำของฉัน: "ไม่เคยใช้=0
"