"शामिल" कॉलम से मेरे WHERE क्लॉज़ को क्यों लाभ होता है?


12

इस उत्तर के अनुसार , जब तक कि उन स्तंभों पर एक इंडेक्स नहीं बनाया जाता है जो प्रतिबंधित करने के लिए उपयोग किए जाते हैं, तो क्वेरी इंडेक्स से लाभान्वित नहीं होगी।

मेरी यह परिभाषा है:

CREATE TABLE [dbo].[JobItems] (
    [ItemId]             UNIQUEIDENTIFIER NOT NULL,
    [ItemState]          INT              NOT NULL,
    [ItemPriority]       INT NOT NULL,
    [CreationTime]       DATETIME         NULL DEFAULT GETUTCDATE(),
    [LastAccessTime]     DATETIME         NULL DEFAULT GETUTCDATE(),
     -- other columns
 );

 CREATE UNIQUE CLUSTERED INDEX [JobItemsIndex]
    ON [dbo].[JobItems]([ItemId] ASC);
 GO

CREATE INDEX [GetItemToProcessIndex]
    ON [dbo].[JobItems]([ItemState], [ItemPriority], [CreationTime])
    INCLUDE (LastAccessTime);
GO

और यह प्रश्न:

UPDATE TOP (150) JobItems 
SET ItemState = 17 
WHERE 
    ItemState IN (3, 9, 10)
    AND LastAccessTime < DATEADD (day, -2, GETUTCDATE()) 
    AND CreationTime < DATEADD (day, -2, GETUTCDATE());

मैंने वास्तविक योजना की समीक्षा की, और वहाँ सिर्फ एक इंडेक्स की तलाश है जैसा कि बिल्कुल सटीक है WHERE- कोई अतिरिक्त "बुकमार्क लुकअप" प्राप्त LastAccessTimeकरने के लिए भले ही बाद वाला केवल इंडेक्स में "शामिल" हो, न कि इंडेक्स का हिस्सा।

यह मुझे ऐसा लगता है कि यह व्यवहार नियम का विरोध करता है कि कॉलम को इंडेक्स का हिस्सा होना चाहिए, न कि केवल "शामिल"।

क्या मेरा व्यवहार सही है? यदि मैं WHEREशामिल कॉलम से अपने लाभ या कॉलम को सूचकांक का हिस्सा बनाने की आवश्यकता है, तो मैं पहले से कैसे जान सकता हूं ?


यह अभी भी ItemStateमूल्य के आधार पर तलाश कर सकता है , हालांकि सीक उतना कुशल नहीं होगा जैसे कि आपका सूचकांक निम्नानुसार संरचित था(ItemState, CreationTime, LastAccessTime)
मार्क सिनकिन्सन

1
@MarkSinkinson या सिर्फ(ItemState, CreationTime) INCLUDE (LastAccessTime)
ypercube

@ लिंक किए गए उत्तर को आप यह नहीं कहते हैं कि ("जब तक कि एक सूचकांक उन स्तंभों पर नहीं बनाया जाता है जो क्वेरी को प्रतिबंधित करने के लिए उपयोग किए जाते हैं, तो एक सूचकांक से लाभ नहीं होगा")। यह कहता है कि किसी इंडेक्स के (a,b)साथ क्वेरी के लिए सबसे अच्छा नहीं है SELECT a FROM t WHERE b=5;और उस पर एक इंडेक्स (b) INCLUDE (a)बहुत बेहतर है।
ypercube y

जवाबों:


9

आपका Predicate आपके Seek Predicate के लिए अलग है।

इंडेक्स में ऑर्डर किए गए डेटा को खोजने के लिए एक सीक प्रेडीकेट का उपयोग किया जाता है। इस मामले में, यह तीन आइटम, प्रत्येक आइटम के लिए एक ऐसा होगा जो आप में रुचि रखते हैं। इसके अलावा, डेटा आइटमपार्टी क्रम में है, इसलिए आगे "सीक" ऑपरेशन नहीं किया जा सकता है।

लेकिन डेटा वापस आने से पहले, यह Predicate का उपयोग करते हुए हर पंक्ति की जांच करता है, जिसे मैं अवशिष्ट प्रेडिकेट के रूप में संदर्भित करता हूं। यह सीक प्रेडिकेट के परिणामों पर किया गया है।

कोई भी शामिल कॉलम ऑर्डर किए गए डेटा का हिस्सा नहीं है, लेकिन इसका उपयोग अतिरिक्त लुकअप किए बिना, अवशिष्ट विधेयकों को संतुष्ट करने के लिए किया जा सकता है।

आप उस सामग्री को देख सकते हैं जो मैंने इस पर लिखा है। विशेष रूप से http://bit.ly/Sargability पर SQLBits के सत्र की जाँच करें

संपादित करें: अवशिष्ट के प्रभाव को बेहतर दिखाने के लिए, अविभाजित का उपयोग करके क्वेरी को चलाएं OPTION (QUERYTRACEON 9130), जो अवशिष्ट को एक अलग फ़िल्टर ऑपरेटर में अलग कर देगा (जो कि वास्तव में योजना का एक पूर्व संस्करण है जो अवशिष्ट को सीक ऑपरेटर में स्थानांतरित करने से पहले)। यह स्पष्ट रूप से एक अप्रभावी सीक के प्रभाव को दिखाता है, फ़िल्टर को छोड़ी गई पंक्तियों की संख्या से।

यह भी ध्यान देने योग्य है कि ItemState में IN क्लॉज होने के कारण, छोड़ा गया डेटा वास्तव में ItemState क्रम में होता है, ItemPriority ऑर्डर में नहीं। आइटम स्टैड पर एक समग्र सूचकांक जिसके बाद एक तारीख (जैसे (आइटमस्टैट, लास्ट एसेटटाइम)) का इस्तेमाल तीन सॉक्स के लिए किया जा सकता है (ध्यान दें सीक प्रेडिक्ट एक सीक ऑपरेटर के भीतर तीन शो दिखाता है), प्रत्येक दो स्तरों के खिलाफ, डेटा का उत्पादन होता है। अभी भी ItemState क्रम में (जैसे, ItemState = 3 और LastAccessTime किसी चीज़ से कम है, फिर ItemState = 9 और LastAccessTime किसी चीज़ से कम है, और फिर ItemState = 10 और LastAccessTime किसी चीज़ से कम)।

(ItemState, LastAccesTime, CreationTime) पर एक इंडेक्स (ItemState, LastAccessTime) पर एक से अधिक उपयोगी नहीं होगा, क्योंकि आपकी सीज़न एक विशेष ItemState और LastSccessTime संयोजन के लिए क्रिएशनटाइम स्तर केवल तभी उपयोगी होता है, जब कोई सीमा नहीं होती है। जैसे अगर आप F में शुरू होने वाले उपनामों में रुचि रखते हैं तो फोन बुक फर्स्टनाम ऑर्डर में कैसे नहीं है।

यदि आप एक कंपोजिट इंडेक्स चाहते हैं, लेकिन आप सीक प्रेडिक्ट्स में बाद के कॉलम का उपयोग करने में सक्षम नहीं हैं, तो जिस तरह से आप पहले वाले कॉलम का उपयोग करते हैं, तो आप उन्हें कॉलम में शामिल कर सकते हैं, जहां वे कम जगह लेते हैं। इंडेक्स (क्योंकि वे केवल इंडेक्स के लीफ लेवल पर स्टोर किए जाते हैं, न कि उच्च स्तर पर) लेकिन फिर भी लुकअप से बच सकते हैं और रेसिडुअल प्रेडिकेट्स में उपयोग किए जा सकते हैं।

अवशिष्ट पद के अनुसार - सीक की इस संपत्ति के लिए मेरा अपना कार्यकाल है। एक मर्ज ज्वाइन ने स्पष्ट रूप से इसे एक अवशिष्ट प्रेडिकेट के बराबर कहा है, और हैश मैच अपने एक प्रोब अवशिष्ट (जिसे आप टीएसए से प्राप्त कर सकते हैं यदि आप हैश से मेल खाते हैं)। लेकिन एक सीक में वे इसे प्रेडिकट कहते हैं जो इसे कम बुरा लगता है।


3

GetItemToProcessIndex पूरी तरह से खोज योग्य नहीं है क्योंकि आपका क्लॉज चालू है ItemState + LastAccessTime + CreationTime। अनुक्रमित कॉलम और जहां क्लॉज एक पूर्ण मिलान नहीं है।

यदि आप ItemState + LastAccessTime + CreationTimeGetItemToProcessIndex से प्राप्त होने वाले प्रत्येक मैच के लिए एक कवरिंग इंडेक्स बनाते हैं, तो आपको अपनी प्राथमिक कुंजी (ItemId) का मूल्य भी मिलता है। यह केवल यह सुनिश्चित करना है कि 2 तारीख एक मैच है।

यह आपको केवल उसके पृष्ठ पर पंक्ति के स्थान पर जाने और उसे अपडेट करने की आवश्यकता है।

आपके वर्तमान सूचकांक के साथ, यह सर्वर को आपके द्वारा इच्छित आइटम के साथ पंक्तियों को खोजने में मदद कर सकता है, लेकिन फिर भी इसे इंडेक्स से उन सभी को पढ़ना होगा, ताकि लास्टअवेस्टटाइम + क्रिएशनटाइम पर सही मिलान मिल सके। तारीख के आधार पर और मिलान सेट के आकार की भविष्यवाणी की जाती है और इसे बाहर रखा जाना चाहिए, इसके परिणामस्वरूप 3 कॉलमों पर पूरी तरह से कवर सूचकांक की तुलना में बहुत अधिक आईओ हो सकता है जो केवल आइटमस्टेट और दूसरा कॉलम (1 अनुक्रमित तारीख) की तलाश करेगा । अनुक्रमित में दूसरी तारीख को हालांकि शामिल किया जा सकता है। इन 3 के बीच अतिरिक्त कॉलम को अनुक्रमित नहीं किया जाना चाहिए, हालांकि यह 4 वें कॉलम के रूप में ठीक हो सकता है (अतिरिक्त कॉलम के बारे में लूट का जवाब देखें)।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.