अनुकूलन समस्या: मिश्रित संकुलित कुंजियाँ, ध्वज की स्थिति और सूचकांक-मर्ज


11

तीन टेबल:

product: कॉलम के साथ: ( a, g, ...a_lot_more... )

a: PK, clustered
g: bit-column

main: कॉलम के साथ: ( c, f, a, b, ...a_lot_more... )

c: PK, clustered
f: bit-column
(a, b): UQ 

lookup कॉलम के साथ: ( a, b, c, i )

(a, b): PK, clustered
a: FK to product(a)
c: UQ, FK to main(c)
i: bit-column

मुझे शामिल होने के लिए अच्छे सूचकांक नहीं मिल सकते हैं:

FROM  
    product
  JOIN 
    lookup
      ON  lookup.a = product.a  
  JOIN
    main
      ON  main.c = lookup.c 
WHERE 
      product.g = 1
  AND
      main.f = 1
  AND 
      lookup.i = 1
  AND lookup.b = 17

मैंने एक कवर इंडेक्स की कोशिश की product (g, a, ...)और इसका उपयोग किया गया, लेकिन शानदार परिणामों के साथ नहीं।

lookupमेज पर अनुक्रमित के कुछ संयोजन पिछली योजना की तुलना में थोड़ी दक्षता हासिल करने के साथ सूचकांक-मर्ज के साथ निष्पादन योजनाएं बनाते हैं।

क्या कोई स्पष्ट संयोजन है जो मुझे याद आ रहा है?

क्या संरचना की फिर से डिजाइन करने में मदद मिल सकती है?

DBMS MySQL 5.5 है और सभी तालिकाएँ InnoDB का उपयोग कर रही हैं।


तालिका आकार:

product: 67K   ,  g applied:    64K 

main:   420K   ,  f applied:   190K

lookup:  12M   ,  b,i applied:  67K 

फ़िल्टर को जोड़ में स्थानांतरित करने का प्रयास करें और देखें कि क्या अनुकूलक इसके साथ कुछ समझदार है या नहीं। मैंने देखा है कि SQL सर्वर के अनुकूलक इससे पहले विफल हो गए हैं।
कंसर्नडऑफटुनब्रिजवेल्स

कार्टेसियन उत्पाद की तरह दिखता है क्योंकि मुझे उत्पाद तालिका से कुछ भी शामिल नहीं दिखता है। या किसी को याद किया था ???
रोलैंडमाइसीडीडीबीए 12

@ रोलैंडमाइसीडीडीबीए: आप सही हैं। मैं प्रश्न सही कर दूंगा।
ypercube y 12

जवाबों:


3

यह मुझे पीड़ा देता है ...

मैं पहले InnoDB के साथ अस्थायी तालिकाओं का उपयोग किया है। उन्हें फ़िल्टर के साथ लोड करें, एक इंडेक्स बनाएं, इन अस्थायी तालिका में शामिल हों।

मुझे लगता है कि समस्या यह है कि यदि InnoDB में केवल नेस्टेड एल्गोरिथ्म शामिल है: बढ़ी हुई RDBMS क्वेरी ऑप्टिमाइज़र का उपयोग करने के लिए अधिक है। यह InnoDB पर डेटा वेयरहाउस प्रकार लोड चलाने की कोशिश पर आधारित है।

अस्थायी तालिकाएँ MySQL क्वेरी ऑप्टिमाइज़र के स्तर के नीचे समग्र जटिलता को बढ़ाती हैं ...


Thnx, मैं कोशिश करूँगा कि। संख्या या पंक्तियाँ (मापदंड लागू होने के बाद क्रमशः उतनी बड़ी, 64K, 67K, 190K नहीं हैं)। हो सकता है कि मैं mainडेटा में अपभ्रंश करके तीन तालिकाओं ( ) में से एक से छुटकारा पाने की कोशिश lookupकरूं?
ypercube y 12

1
@ypercube: अपभ्रंश पंक्तियों को व्यापक बना देगा, कम पृष्ठ घनत्व = अन्य समस्याएं
gbn

3

यह कार्टेशियन उत्पाद जैसा दिखता है। जॉइन मानदंड को फिर से करें

FROM  
    product
  JOIN 
    lookup
      ON  product.a = lookup.a  
  JOIN
    main
      ON  main.c = lookup.c 
WHERE 
      product.g = 1
  AND
      main.f = 1
  AND 
      lookup.i = 1
  AND lookup.b = 17

अलग-अलग सुझाव

यह अपरंपरागत लग सकता है और शायद एसक्यूएल एनीपैटटेन की तरह बदबू आ रही है, लेकिन यहां यह जाता है ...

FROM  
    product
JOIN 
    (
        SELECT * FROM lookup
        WHERE i=1 AND b=17
    ) lookup ON product.a = lookup.a  
JOIN
   main ON main.c = lookup.c 
WHERE 
    product.g = 1 AND main.f = 1

मैंने product.g = 1और main.f = 1उप-क्षेत्रों में स्थानांतरित नहीं किया क्योंकि वे बिट फ़ील्ड हैं और बस बिंदु पर एक टेबल स्कैन करेंगे। यहां तक ​​कि अगर बिट फ़ील्ड इंडेक्स थे, तो क्वेरी ऑप्टिमाइज़र बस ऐसे इंडेक्स को अनदेखा करेगा।

बेशक, आप को बदल सकता है SELECT * FROM lookupकरने के लिए SELECT a FROM lookupसे अगर आपके चयन की जरूरत नहीं है कुछ भीlookup

अगर यह समझ में आता है, मुख्य रूप से लुकअप और मुख्य के बीच ज में बी शामिल है

FROM  
    product
  JOIN 
    lookup
      ON  product.a = lookup.a  
  JOIN
    main
      ON  main.a = lookup.a AND main.b = lookup.b
WHERE 
      product.g = 1
  AND
      main.f = 1
  AND 
      lookup.i = 1
  AND lookup.b = 17

या सी को वापस लाएं और तीन कॉलम में शामिल करें (तीन कॉलम में इंडेक्स mainऔर इन lookup)

FROM  
    product
  JOIN 
    lookup
      ON  product.a = lookup.a  
  JOIN
    main
      ON main.a = lookup.a
      AND main.b = lookup.b
      AND main.c = lookup.c
WHERE 
      product.g = 1
  AND
      main.f = 1
  AND 
      lookup.i = 1
  AND lookup.b = 17

Thnx। विभिन्न प्रदर्शन योजना, लेकिन समान प्रदर्शन।
ypercube y

क्या की प्रमुखता main.fऔर product.g??? यदि मूल्य की 1 के लिए main.fऔर कार्डिनिटी की product.gतालिका पंक्तियों का 5% से कम है, तो एक सूचकांक main.fऔर product.gऔचित्य हो सकता है।
रोलैंडम्यूसीडीडीबीए

कोई बात नहीं, वे पहले से ही अनुक्रमित हैं। यदि की कार्डिनैलिटी main.fऔर product.g2 है, तो आप उन इंडेक्स को खोद सकते हैं।
रोलैंडमाइसीडीडीबीए

तालिका आकार और उपयोग की गई पंक्तियों के साथ प्रश्न संपादित किया (शर्तों के लागू होने के बाद)।
ypercube y

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