2013-09-12 5 views
0

я почти провел день, чтобы оптимизировать этот запрос:MySQL: как оптимизировать этот запрос?

SELECT 
    prod. *, 
    cat.slug category_slug, 
    sup.bname bname, 
    sup.slug bname_slug 
FROM bb_admin.bb_directory_products AS prod 
LEFT JOIN bb_admin.bb_categories_products AS cat 
    ON prod.primary_category_id = cat.category_id 
LEFT JOIN bb_admin.bb_directory_suppliers AS sup 
    ON prod.supplier_id = sup.supplier_id 
LEFT JOIN bb_admin.bb_directory_suppliers AS credit_sup 
    ON prod.credit_supplier_id = credit_sup.supplier_id 
LEFT JOIN bb_admin.bb_directory_suppliers AS photo_sup 
    ON prod.photo_supplier_id = photo_sup.supplier_id 
WHERE (
    prod.status = '1' 
    OR prod.status = '3' 
    OR prod.status = '5' 
) 
    AND (
     sup.active_package_id != '1' 
     OR sup.active_package_id != '5' 
     OR sup.active_package_id != '6' 
     OR prod.supplier_id = '0' 
    ) 
    AND (
     sup.supplier_id = '1989' 
     OR credit_sup.supplier_id = '1989' 
     OR photo_sup.supplier_id = '1989' 
    ) 
GROUP BY prod.product_id 
ORDER BY prod.priority_index ASC 

Можете ли вы помочь мне оптимизировала этот запрос?

+0

Вы можете начать с предупреждения 'SELECT *'. –

+2

Создайте индексы, используйте предложение 'IN()'. – hjpotter92

+0

Какова проблема с производительностью? Насколько велики таблицы? Каков план объяснений? –

ответ

1
  1. Обновления ваших типов данных столбцов, чтобы быть INT или один из его вариантов, так как те, которые вы прибывающие на всех целочисленные идентификаторы (предположение).
  2. Создание индексов на следующие столбцы (если это возможно во всех таблицах):

    • prod.status
    • supplier_id
    • active_package_id
  3. Используйте IN пункт вместо конкатенации OR сегментов.

Я буду помещать обновленный WHERE пункт здесь:

WHERE prod.status IN(1, 3, 5) 
    AND (sup.active_package_id NOT IN(1, 5, 6) 
     OR prod.supplier_id = 0 
    ) 
    AND 1989 IN (prod.supplier_id, prod.credit_supplier_id, prod.photo_supplier_id) 
Смежные вопросы