สิ่งแรกที่คุณต้องรู้คือดัชนีนั้นเป็นวิธีหนึ่งในการหลีกเลี่ยงการสแกนตารางเต็มเพื่อให้ได้ผลลัพธ์ที่คุณต้องการ
มีดัชนีประเภทต่าง ๆ และพวกมันถูกนำไปใช้ในเลเยอร์การจัดเก็บดังนั้นจึงไม่มีมาตรฐานระหว่างพวกเขาและพวกเขายังขึ้นอยู่กับเครื่องมือเก็บข้อมูลที่คุณใช้
InnoDB และดัชนี B + Tree
สำหรับ InnoDB ประเภทดัชนีที่พบบ่อยที่สุดคือดัชนีแบบอิง B + ซึ่งเก็บองค์ประกอบไว้ในลำดับที่เรียงลำดับ นอกจากนี้คุณไม่จำเป็นต้องเข้าถึงตารางจริงเพื่อรับค่าดัชนีซึ่งทำให้การสืบค้นของคุณกลับมาเร็วขึ้น
"ปัญหา" เกี่ยวกับประเภทดัชนีนี้คือคุณต้องค้นหาค่าซ้ายสุดเพื่อใช้ดัชนี ดังนั้นถ้าดัชนีของคุณมีสองคอลัมน์ last_name พูดและ first_name, คำสั่งซื้อที่คุณสอบถามข้อมูลเหล่านี้เป็นเรื่องสำคัญมาก
ดังนั้นให้ตารางต่อไปนี้:
CREATE TABLE person (
last_name VARCHAR(50) NOT NULL,
first_name VARCHAR(50) NOT NULL,
INDEX (last_name, first_name)
);
แบบสอบถามนี้จะใช้ประโยชน์จากดัชนี:
SELECT last_name, first_name FROM person
WHERE last_name = "John" AND first_name LIKE "J%"
แต่อย่างใดอย่างหนึ่งต่อไปนี้จะไม่
SELECT last_name, first_name FROM person WHERE first_name = "Constantine"
เนื่องจากคุณกำลังสืบค้นfirst_name
คอลัมน์ก่อนและไม่ใช่คอลัมน์ซ้ายสุดในดัชนี
ตัวอย่างสุดท้ายนี้ยิ่งแย่ลง:
SELECT last_name, first_name FROM person WHERE first_name LIKE "%Constantine"
เพราะตอนนี้คุณกำลังเปรียบเทียบส่วนขวาสุดของฟิลด์ขวาสุดในดัชนี
ดัชนีแฮช
นี่เป็นดัชนีชนิดอื่นที่น่าเสียดายเฉพาะแบ็กเอนด์หน่วยความจำที่รองรับ มันเร็วฟ้าผ่า แต่เพียงมีประโยชน์สำหรับการค้นหาเต็มรูปแบบซึ่งหมายความว่าคุณไม่สามารถใช้งานได้สำหรับการดำเนินงานชอบ>
, หรือ<
LIKE
เนื่องจากมันใช้งานได้กับแบ็กเอนด์หน่วยความจำเท่านั้นคุณอาจจะไม่ใช้มันบ่อยนัก กรณีหลักที่ฉันนึกได้ตอนนี้คือตารางที่คุณสร้างตารางชั่วคราวในหน่วยความจำพร้อมชุดผลลัพธ์จากตัวเลือกอื่นและทำการเลือกอื่น ๆ จำนวนมากในตารางชั่วคราวนี้โดยใช้ดัชนีแฮช
หากคุณมีVARCHAR
เขตข้อมูลขนาดใหญ่คุณสามารถ "เลียนแบบ" การใช้ดัชนีแฮชเมื่อใช้ B-Tree โดยการสร้างคอลัมน์อื่นและบันทึกค่าที่มีค่ามาก สมมติว่าคุณกำลังเก็บ URL ในฟิลด์และค่ามีขนาดค่อนข้างใหญ่ คุณสามารถสร้างเขตข้อมูลจำนวนเต็มที่เรียกurl_hash
และใช้ฟังก์ชันแฮชเช่นCRC32
หรือฟังก์ชันแฮชอื่น ๆ เพื่อแฮช url เมื่อทำการแทรก จากนั้นเมื่อคุณต้องการสอบถามค่านี้คุณสามารถทำสิ่งนี้:
SELECT url FROM url_table WHERE url_hash=CRC32("http://gnu.org");
ปัญหาของตัวอย่างข้างต้นคือเนื่องจากCRC32
ฟังก์ชั่นสร้างแฮชขนาดเล็กมากคุณจะต้องเจอกับการชนจำนวนมากในค่าแฮช หากคุณต้องการค่าที่แน่นอนคุณสามารถแก้ไขปัญหานี้ได้โดยทำดังนี้
SELECT url FROM url_table
WHERE url_hash=CRC32("http://gnu.org") AND url="http://gnu.org";
ยังคงมีค่าที่จะแฮชสิ่งต่าง ๆ แม้ว่าหมายเลขการชนจะสูงเพราะคุณจะทำการเปรียบเทียบครั้งที่สองเท่านั้น (สตริงที่หนึ่ง) กับแฮชซ้ำแล้วซ้ำอีก
น่าเสียดายที่ใช้เทคนิคนี้คุณยังต้องกดตารางเพื่อเปรียบเทียบurl
ฟิลด์
สรุป
ข้อเท็จจริงบางอย่างที่คุณอาจพิจารณาทุกครั้งที่คุณต้องการพูดคุยเกี่ยวกับการปรับให้เหมาะสม:
การเปรียบเทียบจำนวนเต็มเร็วกว่าการเปรียบเทียบสตริง InnoDB
มันสามารถแสดงตัวอย่างเกี่ยวกับการแข่งขันของกัญชาดัชนีใน
อาจเพิ่มขั้นตอนเพิ่มเติมในกระบวนการทำให้เร็วขึ้นไม่ช้าลง มันสามารถแสดงให้เห็นได้จากข้อเท็จจริงที่ว่าคุณสามารถปรับ a ให้เหมาะสมSELECT
โดยแยกออกเป็นสองขั้นตอนโดยสร้างค่าเก็บหนึ่งในตารางแรกในตารางหน่วยความจำที่สร้างขึ้นใหม่
MySQL มีดัชนีอื่น ๆ ด้วย แต่ผมคิดว่า B + ต้นไม้หนึ่งที่ใช้มากที่สุดที่เคยและกัญชาหนึ่งเป็นสิ่งที่ดีที่จะรู้ แต่คุณสามารถหาคนอื่น ๆ ในเอกสาร MySQL
ฉันขอแนะนำให้คุณอ่านหนังสือ "High Performance MySQL" คำตอบข้างต้นเป็นไปตามบทที่เกี่ยวกับดัชนีอย่างแน่นอน