TOP (และทำไม) ส่งผลกระทบต่อแผนการดำเนินการอย่างไร


35

สำหรับข้อความค้นหาที่ซับซ้อนปานกลางที่ฉันพยายามปรับให้เหมาะสมฉันสังเกตว่าการลบTOP nคำสั่งเปลี่ยนแผนการดำเนินการ ฉันจะเดาว่าเมื่อเคียวรีมีเอ็นจินTOP nฐานข้อมูลจะรันเคียวรีโดยไม่สนใจTOPคำสั่งและจากนั้นในตอนท้ายก็ลดขนาดของผลลัพธ์ที่กำหนดไว้เป็นจำนวนแถวnที่ถูกร้องขอ แผนการดำเนินการกราฟิกดูเหมือนว่าจะระบุว่าเป็นกรณีนี้ - TOPเป็นขั้นตอน "สุดท้าย" แต่ดูเหมือนว่าจะเกิดขึ้นมากขึ้น

คำถามของฉันคือประโยค TOP และ N มีผลอย่างไรต่อแผนการดำเนินการของแบบสอบถาม

นี่เป็นเวอร์ชั่นที่เรียบง่ายของสิ่งที่เกิดขึ้นในกรณีของฉัน:

แบบสอบถามกำลังจับคู่แถวจากสองตาราง A และ B

โดยไม่ต้องTOPเป็นไปตามข้อเพิ่มประสิทธิภาพประเมินจะมี 19k แถวจากตารางและ 46K แถวจากตาราง B. จำนวนที่เกิดขึ้นจริงของแถวกลับเป็น 16k สำหรับ A และ 13k สำหรับการแข่งขันบีกัญชาจะใช้ในการเข้าร่วมทั้งสองชุดผลลัพธ์ รวม 69 แถว (จากนั้นจะใช้การเรียงลำดับ) แบบสอบถามนี้เกิดขึ้นอย่างรวดเร็วมาก

เมื่อฉันเพิ่มTOP 1001เครื่องมือเพิ่มประสิทธิภาพไม่ได้ใช้แฮชจับคู่; แต่ก่อนจะเรียงลำดับผลลัพธ์จากตาราง A (ประมาณเดียวกัน / เป็นจริงของ 19k / 16k) และทำการวนซ้ำซ้อนกับตาราง B จำนวนแถวของตาราง B ที่ประมาณในขณะนี้คือ 1 และสิ่งที่แปลกก็คือสิ่งที่TOP nส่งผลโดยตรงต่อ ประเมินจำนวนการประหารชีวิต (ดัชนีแสวงหา) กับ B - มันดูเหมือนจะเป็นเสมอ2n + 1หรือในกรณีของฉัน 2003 TOP nประมาณนี้มีการเปลี่ยนแปลงตามความเหมาะสมหากฉันเปลี่ยน แน่นอนเนื่องจากนี่คือการรวมที่ซ้อนกันจำนวนจริงของการประมวลผลคือ 16k (จำนวนแถวจากตาราง A) และสิ่งนี้ทำให้การสืบค้นช้าลง

สถานการณ์ที่เกิดขึ้นจริงนั้นซับซ้อนกว่านี้เล็กน้อย แต่สิ่งนี้จะรวบรวมความคิด / พฤติกรรมพื้นฐาน ตารางทั้งสองถูกค้นหาโดยใช้ดัชนีค้นหา นี่คือ SQL Server 2008 R2 Enterprise edition


แบบสอบถามมีORDER BYข้อ การเพิ่มTOPการเปลี่ยนแปลงที่ในแผนแบบนี้เกิดขึ้น แต่ฉันกังวลมากขึ้นว่ามันมีผลต่อจำนวนการดำเนินการของดัชนีที่ค้นหาเทียบกับตาราง B ... (แน่นอนว่าทั้งสองอาจเกี่ยวข้องกัน - ฉันไม่รู้)
เดวิด

1
การสนทนาที่เกี่ยวข้อง: FAST num_rowsคำใบ้คำถาม
Remus Rusanu

คำตอบ:


38

ฉันจะเดาได้ว่าเมื่อเคียวรีรวมท็อปเอ็นเอ็นเอ็นจิ้นฐานข้อมูลจะรันเคียวรีโดยไม่สนใจคำสั่ง TOP และท้ายที่สุดเพียงลดขนาดผลลัพธ์ที่ตั้งไว้เป็นจำนวนแถวที่ร้องขอ แผนการดำเนินการกราฟิกดูเหมือนว่าจะระบุว่าเป็นกรณีนี้ - TOP คือขั้นตอน "สุดท้าย" แต่ดูเหมือนว่าจะเกิดขึ้นมากขึ้น

วิธีที่กล่าวมาข้างต้นทำให้ฉันคิดว่าคุณอาจมีภาพจิตที่ไม่ถูกต้องว่าแบบสอบถามดำเนินการอย่างไร ตัวดำเนินการในแผนแบบสอบถามไม่ใช่ขั้นตอน (โดยที่ชุดผลลัพธ์แบบเต็มของขั้นตอนก่อนหน้าจะได้รับการประเมินโดยชุดถัดไป

SQL Server ใช้ไปป์ไลน์รูปแบบการดำเนินการที่ผู้ประกอบการแต่ละ exposes วิธีการเช่นInit () , GetRow ()และปิด () ตามที่ชื่อGetRow ()แนะนำตัวดำเนินการจะสร้างหนึ่งแถวต่อครั้งตามต้องการ (ตามที่ผู้ดำเนินการหลักกำหนดไว้) นี้ถูกบันทึกไว้ในหนังสือออนไลน์ตรรกะและผู้ประกอบการทางกายภาพอ้างอิงกับรายละเอียดในการโพสต์บล็อกของฉันทำไมแบบสอบถามแผนเรียกใช้ย้อนกลับ แบบจำลองแถวต่อครั้งนี้มีความสำคัญในการสร้างสัญชาตญาณเสียงสำหรับการดำเนินการค้นหา

คำถามของฉันคือTOPn clause (และทำไม) ส่งผลกระทบต่อแผนการดำเนินการของแบบสอบถามอย่างไร

การดำเนินการเชิงตรรกะบางอย่างเช่นการTOPรวมกึ่งและFAST n คำแนะนำการสืบค้นมีผลต่อวิธีที่เครื่องมือเพิ่มประสิทธิภาพการสืบค้นใช้ต้นทุนทางเลือกแผนการดำเนินการ แนวคิดพื้นฐานคือรูปร่างของแผนที่เป็นไปได้หนึ่งอาจส่งคืนแถวnแถวแรกได้เร็วกว่าแผนอื่นที่ปรับให้เหมาะกับการส่งคืนแถวทั้งหมด

ตัวอย่างเช่นการเข้าร่วมลูปแบบซ้อนที่จัดทำดัชนีมักเป็นวิธีที่เร็วที่สุดในการส่งคืนแถวจำนวนเล็กน้อยแม้ว่าการแฮชหรือการรวมการรวมกับการสแกนอาจมีประสิทธิภาพมากกว่าในชุดที่มีขนาดใหญ่กว่า วิธีที่เหตุผลของเครื่องมือเพิ่มประสิทธิภาพการสืบค้นเกี่ยวกับตัวเลือกเหล่านี้คือการตั้งค่าเป้าหมายแถวที่จุดใดจุดหนึ่งในแผนผังการทำงานแบบลอจิคัล

เป้าหมายแถวจะปรับเปลี่ยนวิธีคิดต้นทุนทางเลือกแผนแบบสอบถาม สาระสำคัญของมันคือการที่เครื่องมือเพิ่มประสิทธิภาพเริ่มต้นด้วยการคิดต้นทุนผู้ประกอบการแต่ละรายราวกับว่าจำเป็นต้องใช้ชุดผลลัพธ์แบบเต็มตั้งเป้าหมายแถวที่จุดที่เหมาะสม เพื่อให้บรรลุเป้าหมายของแถว

ตัวอย่างเช่นลอจิคัลTOP(10)ตั้งค่าเป้าหมายแถว 10 ที่จุดใดจุดหนึ่งในแผนผังคิวรีแบบลอจิคัล ค่าใช้จ่ายของผู้ประกอบการที่นำไปสู่เป้าหมายของแถวถูกปรับเปลี่ยนเพื่อประเมินจำนวนแถวที่พวกเขาต้องการในการผลิตเพื่อให้บรรลุเป้าหมายแถว การคำนวณนี้อาจซับซ้อนดังนั้นจึงง่ายต่อการเข้าใจทั้งหมดนี้ด้วยตัวอย่างการทำงานอย่างสมบูรณ์และแผนการดำเนินการที่มีคำอธิบายประกอบ เป้าหมายแถวสามารถส่งผลมากกว่าตัวเลือกประเภทการเข้าร่วมหรือการค้นหาและการค้นหาที่ต้องการสแกน รายละเอียดเพิ่มเติมเกี่ยวกับที่นี่

เช่นเคยแผนการดำเนินการที่เลือกตามเป้าหมายของแถวจะขึ้นอยู่กับความสามารถในการใช้เหตุผลของเครื่องมือเพิ่มประสิทธิภาพและคุณภาพของข้อมูลที่ให้ไว้ ไม่ใช่ทุกแผนที่มีเป้าหมายแถวจะสร้างจำนวนแถวที่ต้องการได้เร็วขึ้นในทางปฏิบัติ แต่ตามรูปแบบการคิดต้นทุน

ในกรณีที่แผนเป้าหมายแถวพิสูจน์ได้ว่าไม่เร็วกว่าปกติแล้วจะมีวิธีแก้ไขแบบสอบถามหรือให้ข้อมูลที่ดีขึ้นแก่เครื่องมือเพิ่มประสิทธิภาพเพื่อให้แผนเลือกโดยธรรมชาติดีที่สุด ตัวเลือกใดที่เหมาะสมในกรณีของคุณขึ้นอยู่กับรายละเอียดของหลักสูตร โดยทั่วไปคุณสมบัติของแถวเป้าหมายนั้นมีประสิทธิภาพมาก (แม้ว่าจะมีข้อผิดพลาดที่ต้องระวังเมื่อใช้ในแผนปฏิบัติการแบบขนาน)

แบบสอบถามและแผนเฉพาะของคุณอาจไม่เหมาะสำหรับการวิเคราะห์อย่างละเอียดที่นี่ (โดยทั้งหมดให้แผนปฏิบัติการจริงหากคุณต้องการ) แต่หวังว่าแนวคิดที่อธิบายไว้ที่นี่จะช่วยให้คุณสามารถดำเนินการต่อไปได้


12

เมื่อคุณใช้ TOP เครื่องมือเพิ่มประสิทธิภาพจะมองเห็นโอกาสในการทำงานน้อยลง หากคุณขอ 10 แถวอาจมีโอกาสที่ดีที่คุณไม่จำเป็นต้องใช้ทั้งชุด ดังนั้นผู้ใช้งาน TOP สามารถผลักไปทางขวาได้มากขึ้น มันจะขอแถวจากโอเปอเรเตอร์ถัดไป (ทางขวา) จนกว่าจะได้รับเพียงพอ

คุณชี้ให้เห็นว่าหากไม่มี TOP การสืบค้นจะเรียงลำดับข้อมูลที่ส่วนท้ายสุด หากเครื่องยนต์ทราบจำนวนแถวที่จะพึงพอใจจากการเข้าร่วมล่วงหน้ามันอาจเลือกที่จะใช้แผนการที่คล้ายกันโดยวางตำแหน่ง TOP ทางด้านซ้าย แต่ด้วยความพยายามที่จะทำการแข่งขัน Hash ค่อนข้างสูงและไม่มีทางเลือกอื่นสำหรับการเข้าร่วมผสานเครื่องมือเพิ่มประสิทธิภาพอาจต้องการกรอง TOP ไปทางขวามากขึ้น

เมื่อมีการสอบถามตาราง B การดึงข้อมูลครั้งละหนึ่งแถว นั่นเป็นสาเหตุที่การประมาณเป็น 1 และยังสันนิษฐานว่ามันจะพบว่าแถวนั้น 50% ของเวลาเท่านั้น ดังนั้นมันจึงเดาได้ว่ามันต้องใช้ 2n +1 เพื่อหามัน


ดูเหมือนจะไม่ถูกต้องว่าจำนวนแถวโดยประมาณจะเปลี่ยนไปตามวิธีการดึงข้อมูล การรับข้อมูลไม่ควรส่งผลกระทบต่อความเป็นหัวใจ การเปลี่ยนแปลงในวิธีการดึงข้อมูลนั้นจะสะท้อนให้เห็นในจำนวนการประหารชีวิตใช่ไหม?
David

"จำนวนแถวโดยประมาณ" ต่อการดำเนินการ ใน Nested Loop มีโอกาสที่จะเรียกใช้มากกว่าหนึ่งครั้ง
Rob Farley

นี่จะเป็นพฤติกรรมที่แตกต่างจากจำนวนแถวจริงและจำนวนการเรียกใช้ (จริง) หากแผนจริงแสดงการดำเนินการจริง 16,834 ครั้งและส่งคืนแถวจริง 15,407 แถวฉันใช้สิ่งนี้เพื่อแสดงว่าได้ 16k ค้นหา แต่พบเพียง 15k ที่ตรงกับภาคแสดง ถ้ามันหมายถึง 15k แถวต่อการดำเนินการนี้จะเป็น 15k * 16k = 240 ล้านแถว - ใหญ่กว่าตารางประมาณ 10 เท่า ...
David

นอกจากนี้ฉันไม่แน่ใจว่าฉันทำตามคำสั่งสุดท้ายของคำตอบของคุณ เมื่อคุณพูดว่า 2n +1 ให้ค้นหา "มัน" คุณหมายถึงอะไร "it"? ไม่แถวเดียวแน่นอน คุณหมายความว่าเครื่องมือเพิ่มประสิทธิภาพสมมติว่าสำหรับแถวที่กำหนดใน A มีโอกาส 50% ที่จะถูกจับคู่กับ B ดังนั้นจึงจำเป็นต้อง "ลอง" 2003 แถวจาก A เพื่อรับ 1001 การแข่งขันจาก B หรือไม่ พฤติกรรมนี้มีการบันทึกไว้ทุกที่โดย Microsoft หรือไม่ และมันเกี่ยวอะไรกับTOPประโยค? ขอบคุณสำหรับคำตอบ / ความอดทนของคุณ
เดวิด

ใช่แถวโดยประมาณคือต่อการดำเนินการ แถวที่แท้จริงคือผลรวม แม้ว่าจะไม่มีปัญหาในการให้ตัวดำเนินการส่งคืนแถวมากกว่าที่อยู่ในตารางเนื่องจากมันง่ายมากที่จะแสดงตัวดำเนินการที่ส่งคืนแถวเดียวกันหลาย ๆ ครั้ง
Rob Farley
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.