Проблема с производительностью в случае запроса SQL Match Against для нескольких таблиц

Я столкнулся с проблемой производительности при выполнении SQL-запроса, использующего базу данных MyISAM.

Вкратце, у меня есть 3 таблицы:
Таблица: A (Двигатель MyISAM. Всего записей: 1847)
Таблица: B (Двигатель MyISAM. Всего записей: 1110)
Таблица: C (Двигатель MyISAM. Всего записей: 1110)
Таблица: C (Двигатель MyISAM. Всего записей: 1847) MyISAM. Всего записей: 57867)

Теперь запрос, который я запускаю, занимает 623 секунды, и иногда случается, что соединение с сервером (то же самое в случае с локальным хостом) прерывается.

Ниже приведен запрос, который я выполняю:

SELECT MATCH(A.title, A.description) AGAINST('Computer Graphic Artist') AS 'Score',
    A.code AS 'Code',
    B.cluster AS 'Cluster',
    B.pathway AS 'Pathway',
    A.title AS 'Role',
    A.description AS 'Description'
FROM B
INNER JOIN A ON B.code = A.code
INNER JOIN C ON B.code = C.code
WHERE MATCH(A.title, A.description) AGAINST('Computer Graphic Artist')
  OR MATCH(B.cluster, B.pathway, B.descripton) AGAINST('Computer Graphic Artist')
  OR MATCH(C.title) AGAINST('Computer Graphic Artist')
ORDER BY Score DESC, B.cluster ASC

Вы также можете обратиться к Pastie (если вы не видите этот SQL). Я добавил свойство FULLTEXT везде, где это применимо.

ПРИМЕЧАНИЕ. В таблицах A, B и C также есть несколько повторяющихся записей.

Пожалуйста, дайте мне знать, как я могу оптимизировать этот SQL для быстрого вывода.


person Puneet Pandey    schedule 20.07.2012    source источник
comment
@Neville: Что именно ты хочешь, чтобы я сюда прикрепил?   -  person Puneet Pandey    schedule 22.07.2012


Ответы (1)


Первое, что нужно сделать, это убедиться, что у вас есть FULLTEXT индекс для точного набора столбцов, которые вы запрашиваете из каждой таблицы:

alter table A add fulltext index a_fti (title,description);
alter table B add fulltext index b_fti (cluster, pathway, descripton);
alter table C add fulltext index c_fti (title);

Тогда я бы рекомендовал переписать ваш запрос, чтобы использовать UNION вместо OR. Я получил гораздо лучшую производительность от поиска FULLTEXT, в частности, в MySQL, используя этот подход.

Вот пример использования вашего запроса:

select Score, Code, Cluster, Pathway, Role, Description
from
(
SELECT MATCH(A.title, A.description) AGAINST('Computer Graphic Artist') AS 'Score',
    A.code AS 'Code',
    B.cluster AS 'Cluster',
    B.pathway AS 'Pathway',
    A.title AS 'Role',
    A.description AS 'Description'
FROM B
INNER JOIN A ON B.code = A.code
INNER JOIN C ON B.code = C.code
WHERE MATCH(A.title, A.description) AGAINST('Computer Graphic Artist')
UNION
SELECT MATCH(A.title, A.description) AGAINST('Computer Graphic Artist') AS 'Score',
    A.code AS 'Code',
    B.cluster AS 'Cluster',
    B.pathway AS 'Pathway',
    A.title AS 'Role',
    A.description AS 'Description'
FROM B
INNER JOIN A ON B.code = A.code
INNER JOIN C ON B.code = C.code
WHERE MATCH(B.cluster, B.pathway, B.descripton) AGAINST('Computer Graphic Artist')
UNION
SELECT MATCH(A.title, A.description) AGAINST('Computer Graphic Artist') AS 'Score',
    A.code AS 'Code',
    B.cluster AS 'Cluster',
    B.pathway AS 'Pathway',
    A.title AS 'Role',
    A.description AS 'Description'
FROM B
INNER JOIN A ON B.code = A.code
INNER JOIN C ON B.code = C.code
WHERE MATCH(C.title) AGAINST('Computer Graphic Artist')
) as sub_query
ORDER BY Score DESC, Cluster ASC
person Ike Walker    schedule 20.07.2012
comment
Спасибо @IkeWalker за ответ. Я выполнил ваш первый шаг. Во-вторых, когда вы предложили мне использовать UNION, я попробую (только тогда я был бы в состоянии сказать вам, понял ли я лучший o/p с точки зрения производительности). Но хотел бы знать ( увидев измененный запрос), он намного больше, чем оригинал, как UNION отличит его от условия OR (если мы говорим об этом конкретном случае). Ваш ответ был бы очень полезен для меня, чтобы узнать это подробно. - person Puneet Pandey; 22.07.2012
comment
Привет @Ike: я попробовал подход, который вы предложили мне выше, и теперь я вижу улучшение производительности :-) Теперь запрос занимает 54 секунды, чтобы получить результат. Тем не менее, я хотел бы знать, можем ли мы оптимизировать его здесь!! Еще одна вещь: поскольку это работает в среде разработки, поэтому я могу ожидать более быстрого o/p после выполнения этого запроса на производственном или реальном сервере. Ищу ваш ценный ответ. Большое спасибо за помощь :-) - person Puneet Pandey; 23.07.2012