क्या गैर-प्रासंगिक कॉलम चुनिंदा कथनों के क्वेरी समय को प्रभावित करते हैं?


10

मैं सिर्फ उत्सुक हूँ।

कहें कि आपके पास 1 मिलियन रिकॉर्ड / पंक्तियों की एक तालिका है।

select order_value from store.orders

क्या इससे कोई फर्क पड़ता है कि क्या वास्तविक क्वेरी समय में उस तालिका में 1 फ़ील्ड, 2 फ़ील्ड या 100 फ़ील्ड हैं? मेरा मतलब है कि सभी क्षेत्रों के अलावा "order_value।"

अभी मैं डेटा को डेटा वेयरहाउस में धकेल रहा हूं। कभी-कभी मैं खेतों को तालिका में डुबो देता हूं कि "किसी दिन भविष्य में उपयोग किया जा सकता है" - लेकिन वे अभी किसी भी चीज से विमुख नहीं हो रहे हैं। क्या ये 'बहिर्मुखी' क्षेत्र उन चुनिंदा बयानों को प्रभावित करेंगे जिनमें कोई प्रत्यक्ष या अप्रत्यक्ष रूप से शामिल नहीं है (नहीं * मेरा मतलब है)?


वेब पर इस पर उपलब्ध जानकारी के टन है। प्रौद्योगिकी परिवर्तन के रूप में कुंजी सबसे हाल की जानकारी प्राप्त कर रही है। आप जो पूछ रहे हैं, वह आपके विशेष सेटअप पर इतना निर्भर है कि बहुत अच्छा जवाब देना संभव नहीं है। याद रखने की एक महत्वपूर्ण बात यह है कि जैसे ही हम SSD में जाते हैं, कई चीजें जो एक बार प्रदर्शन के लिए बहुत महत्वपूर्ण थीं, अब ऐसा नहीं है।
जो

जवाबों:


10

यह वास्तव में अनुक्रमित और डेटा प्रकारों पर निर्भर करता है।

एक उदाहरण के रूप में स्टैक ओवरफ़्लो डेटाबेस का उपयोग करना, यह वही है जो उपयोगकर्ता तालिका जैसा दिखता है:

पागल

इसमें Id कॉलम पर PK / CX है। तो यह आईडी द्वारा क्रमबद्ध तालिका डेटा की संपूर्णता है।

इसके साथ ही एकमात्र इंडेक्स के रूप में, SQL को उस पूरी चीज़ (LOB कॉलम को सेंस) में पढ़ना पड़ता है अगर यह पहले से ही नहीं है।

DBCC DROPCLEANBUFFERS-- Don't run this anywhere near prod.

SET STATISTICS TIME, IO ON 

SELECT u.Id
INTO  #crap1
FROM dbo.Users AS u

आँकड़े समय और io प्रोफ़ाइल इस तरह दिखता है:

Table 'Users'. Scan count 7, logical reads 80846, physical reads 0, read-ahead reads 0, lob logical reads 0, lob physical reads 0, lob read-ahead reads 0.

 SQL Server Execution Times:
   CPU time = 2406 ms,  elapsed time = 446 ms.

अगर मैं सिर्फ Id पर एक अतिरिक्त गैर-अनुक्रमित सूचकांक जोड़ता हूं

CREATE INDEX ix_whatever ON dbo.Users (Id)

अब मेरे पास एक बहुत छोटा सूचकांक है जो मेरी क्वेरी को संतुष्ट करता है।

DBCC DROPCLEANBUFFERS-- Don't run this anywhere near prod.

SELECT u.Id
INTO  #crap2
FROM dbo.Users AS u

यहाँ प्रोफ़ाइल:

Table 'Users'. Scan count 7, logical reads 6587, physical reads 0, read-ahead reads 6549, lob logical reads 0, lob physical reads 0, lob read-ahead reads 0.

 SQL Server Execution Times:
   CPU time = 2344 ms,  elapsed time = 384 ms.

हम बहुत कम पढ़ते हैं और थोड़ा CPU समय बचा पाते हैं।

आपकी तालिका परिभाषा के बारे में अधिक जानकारी के बिना, मैं वास्तव में वह पुन: उत्पन्न करने का प्रयास नहीं कर सकता जो आप किसी भी बेहतर को मापने की कोशिश कर रहे हैं।

लेकिन आप कह रहे हैं कि जब तक उस एकल स्तंभ पर कोई विशिष्ट सूचकांक नहीं होगा, तब तक अन्य कॉलम / फ़ील्ड भी स्कैन किए जाएंगे? क्या यह केवल रोड़े की तालिकाओं के डिजाइन के लिए एक दोष है? अप्रासंगिक क्षेत्र क्यों स्कैन किए जाएंगे?

हां, यह पंक्तिस्टोर तालिकाओं के लिए विशिष्ट है। डेटा पेज पर पंक्ति द्वारा डेटा संग्रहीत किया जाता है। भले ही पृष्ठ का अन्य डेटा आपकी क्वेरी के लिए अप्रासंगिक हो, लेकिन उस पूरी पंक्ति> पृष्ठ> सूचकांक को स्मृति में पढ़ने की आवश्यकता है। मैं यह नहीं कहूंगा कि अन्य कॉलम "स्कैन" किए गए हैं, क्योंकि वे जिस पृष्ठ पर मौजूद हैं, वह क्वेरी के लिए प्रासंगिक उन पर एकल मान प्राप्त करने के लिए स्कैन किया गया है।

Ol 'फोनबुक उदाहरण का उपयोग करना: भले ही आप फ़ोन नंबर पढ़ रहे हों, जब आप पृष्ठ को चालू करते हैं, तो आप फ़ोन नंबर के साथ अंतिम नाम, पहला नाम, पता आदि बदल रहे हैं।


@ jpmc26 यह इससे भी बदतर हो सकता है, क्योंकि यदि अनुरोध किए गए कॉलम एक इंडेक्स का हिस्सा हैं, तो क्वेरी को केवल इंडेक्स को देखकर ही परोसा जा सकता है। यदि स्तंभों को अनुक्रमित नहीं किया जाता है, तो वे प्राथमिक रिकॉर्ड लोड होने का कारण बन सकते हैं, और यहां तक ​​कि गैर-अभिहित तालिका / स्तंभ प्रकारों के लिए माध्यमिक रिकॉर्ड भी।
क्रिस्टोफर

12

यह तालिका संरचना और उपलब्ध अनुक्रमित पर निर्भर करता है।

  • केस ए: आम (रोस्टोर) तालिका, कोई सूचकांक नहीं (order_value)

    एकमात्र संभव निष्पादन योजना पूरी तालिका को पढ़ना है (जो कि 2 बनाम 200 कॉलम होने पर निश्चित रूप से बहुत अलग है, इसलिए कुछ बनाम कुछ हजार बाइट्स चौड़ी हैं)।

  • केस B: सामान्य तालिका में, (order_value)उस स्तंभ पर कोई अनुक्रमणिका या कुछ अन्य अनुक्रमणिकाएँ होती हैं।

    अब एक बेहतर योजना है, पूरे सूचकांक (उनमें से एक) को स्कैन करें - जो निश्चित रूप से पूरी मेज की तुलना में बहुत अधिक संकीर्ण है, बस कुछ बाइट्स। यदि अप्रासंगिक हो जाता है यदि तालिका में 2 या 200 कॉलम हैं। केवल सूचकांक स्कैन किया जाता है।

  • केस C: यह एक कॉलमस्टोर टेबल है।

    जैसा कि नाम से ही स्पष्ट है कि इन तालिकाओं की संरचना स्तंभ-वार उन्मुख है, न कि पंक्ति-वार। किसी भी सूचकांक की कोई आवश्यकता नहीं है, टेबल डिजाइन ही पूरे कॉलम को पढ़ने के लिए अनुकूल है।


मेरा ज्ञान इस मुद्दे पर थोड़ा हरा है। यह सबसे पारंपरिक है (विशिष्ट एसक्यूएल सर्वर डेटाबेस कहते हैं) रोस्टोरेज टेबल, सही है? यदि केवल एक कॉलम / फ़ील्ड को वापस करने की आवश्यकता है, तो पूरी तालिका को स्कैन क्यों किया जाएगा? क्या यह केवल रोस्टोरेंट टेबल के डिज़ाइन के लिए अंतर्निहित है?
उपयोगकर्ता 45867

@ user45867 हाँ, डेटा पंक्तियों में संग्रहीत हैं (कुछ बहुत बड़े स्तंभों को छोड़कर जो बाहर संग्रहीत हैं)। जब SQL सर्वर डिस्क से पढ़ता है, तो यह पूरे ब्लॉक में पढ़ता है, यह केवल उस हिस्से को नहीं पढ़ सकता है जिसमें एक कॉलम है।
ypercube y
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.