ฉันไม่คิดว่ามันจะเกี่ยวอะไรกับการช้าอย่างน่ากลัว มันเกี่ยวข้องกับความไม่ถูกต้องที่อาจเกิดขึ้น ตัวอย่างเช่นให้ข้อมูลต่อไปนี้ - คำสั่งซื้อที่สามารถส่งโดยลูกค้ารายบุคคลหรือพันธมิตร B2B:
DECLARE @Customers TABLE(CustomerID INT);
INSERT @Customers VALUES(1),(2);
DECLARE @Orders TABLE(OrderID INT, CustomerID INT, CompanyID INT);
INSERT @Orders VALUES(10,1,NULL),(11,NULL,5);
สมมติว่าฉันต้องการค้นหาลูกค้าทั้งหมดที่ไม่เคยสั่งซื้อ ได้รับข้อมูลมีเพียงหนึ่ง: ลูกค้า # 2 ต่อไปนี้เป็นสามวิธีที่ฉันจะเขียนแบบสอบถามเพื่อค้นหาข้อมูล (มีวิธีอื่น):
SELECT [NOT IN] = CustomerID FROM @Customers
WHERE CustomerID NOT IN (SELECT CustomerID FROM @Orders);
SELECT [NOT EXISTS] = CustomerID FROM @Customers AS c
WHERE NOT EXISTS (SELECT 1 FROM @Orders AS o
WHERE o.CustomerID = c.CustomerID);
SELECT [EXCEPT] = CustomerID FROM @Customers
EXCEPT SELECT CustomerID FROM @Orders;
ผล:
NOT IN
------
-- <-- no results. Is that what you expected?
NOT EXISTS
----------
2
EXCEPT
------
2
ตอนนี้มีปัญหาเรื่องประสิทธิภาพด้วยเช่นกันและฉันก็พูดถึงมัน ในโพสต์บล็อกนี้ ขึ้นอยู่กับข้อมูลและดัชนีNOT EXISTS
มักจะมีประสิทธิภาพสูงกว่าNOT IN
และฉันไม่รู้ว่ามันจะทำงานได้แย่ลงหรือไม่ คุณควรทราบว่าEXCEPT
สามารถแนะนำการดำเนินการเรียงลำดับที่แตกต่างกันดังนั้นคุณอาจจบลงด้วยข้อมูลที่แตกต่างกัน (อีกครั้งขึ้นอยู่กับแหล่งที่มา) และLEFT OUTER JOIN ... WHERE right.column IS NULL
รูปแบบที่นิยมมักจะเป็นนักแสดงที่แย่ที่สุดเสมอ
Martin Smith มีข้อมูลสนับสนุนที่ดีมากมายในคำตอบของเขาใน SO เช่นกันกัน
IN
/NOT IN
จะถูกนำมาใช้กับลูปซ้อนกันเสมอ และฉันไม่รู้ว่าstops SQL Server from creating a ‘plan’
ควรจะหมายถึงอะไร