Мастера SQL, помогите

12
imbalance
На сайте с 03.03.2007
Offline
240
1596

Коллеги,

Есть БД MySql, и подобный запрос:

SELECT dle_comments.id, post_id, allow_edit,rating_plus, rating_minus, dle_comments.user_id, dle_comments.date, dle_comments.autor as gast_name, dle_comments.is_deleted, dle_comments.email as gast_email, text, ip, is_register, name, dle_users.email, news_num, dle_users.comm_num, user_group, reg_date, signature, foto, fullname, land, icq, dle_users.xfields, dle_post.title, dle_post.approve, dle_post.date as newsdate, dle_post.alt_name, dle_post.category, dle_post.flag FROM dle_comments LEFT JOIN dle_post ON dle_comments.post_id=dle_post.id LEFT JOIN dle_users ON dle_comments.user_id=dle_users.user_id WHERE dle_comments.approve='1' AND dle_comments.is_deleted='0' AND dle_post.approve=1 ORDER BY id desc LIMIT 272010,10

Запрос очень тяжелый, таблицы очень-очень огромные.

Какие варианты есть для оптимизации?

Помогут ли тут индексы?

Знающие люди, подскажите :)

C
На сайте с 04.02.2005
Offline
291
#1

SELECT dle_comments.id, post_id, allow_edit,rating_plus, 

rating_minus, dle_comments.user_id, dle_comments.date,
dle_comments.autor as gast_name,
dle_comments.is_deleted, dle_comments.email as gast_email,
text, ip, is_register, name, dle_users.email, news_num,
dle_users.comm_num, user_group, reg_date, signature, foto,
fullname, land, icq, dle_users.xfields, dle_post.title,
dle_post.approve, dle_post.date as newsdate, dle_post.alt_name,
dle_post.category, dle_post.flag
FROM dle_comments
LEFT JOIN dle_post ON dle_comments.post_id=dle_post.id AND dle_post.approve=1
LEFT JOIN dle_users ON dle_comments.user_id=dle_users.user_id
WHERE dle_comments.approve='1'
AND dle_comments.is_deleted='0'
ORDER BY id desc LIMIT 272010,10

Чуть-чуть... красивше :)

L
На сайте с 07.12.2007
Offline
351
#2
imbalance:
Какие варианты есть для оптимизации?
Помогут ли тут индексы?

Устанавливаете бесплатную замечательную программу HeidiSQL - это типа phpmyadmin, но в сто раз круче (я даже не поленилась и donation автору отправила).

Получаете отменный user frendly GUIвизуальный доступ к своей БД, к котором можно добавить/удалить индексы, отладить любые SQL-запросы, и посмотреть время их выполнения, импортировать и экспортировать базы, смотреть статистику.

Вбиваете свой запрос туда и отлаживаете его прямо на ваших реальных таблицах. Смотрите explain запроса - какие индексы использует mysql при запросе, создаются ли временные таблицы, ...

PS: Иногда "select from select ..." работает быстрее чем объединение таблиц по join. Но это надо по экспериментировать на реальных таблицах.

PPS: HeidiSQL подключается к БД удалённо, надо чтобы у хостера был открыт наружу порт 3306. И уровень доступа к бд был не localhost(принимать подключения только внутри сервера), а %(с любого IP) или указан конкретный IP

PPPS: Select-ами - не накосячишь, а с запросами delete from table или drop db/drop table - аккуратнее, можно снести всё за 5 сек.

bukachuk
На сайте с 07.09.2008
Offline
97
#3

EXPLAIN вставьте перед запросом и покажите результат. Или точнее сделайте запрос в базу

EXPLAIN SELECT dle_comments.id, post_id, allow_edit,rating_plus,
rating_minus, dle_comments.user_id, dle_comments.date,
dle_comments.autor as gast_name,
dle_comments.is_deleted, dle_comments.email as gast_email,
text, ip, is_register, name, dle_users.email, news_num,
dle_users.comm_num, user_group, reg_date, signature, foto,
fullname, land, icq, dle_users.xfields, dle_post.title,
dle_post.approve, dle_post.date as newsdate, dle_post.alt_name,
dle_post.category, dle_post.flag
FROM dle_comments
LEFT JOIN dle_post ON dle_comments.post_id=dle_post.id AND dle_post.approve=1
LEFT JOIN dle_users ON dle_comments.user_id=dle_users.user_id
WHERE dle_comments.approve='1'
AND dle_comments.is_deleted='0'
ORDER BY id desc LIMIT 272010,10

еще результаты:

SHOW INDEX FROM dle_post;

SHOW INDEX FROM dle_comments;

SHOW INDEX FROM dle_users;

Программирование PHP,Mysql (/ru/forum/934470)
imbalance
На сайте с 03.03.2007
Offline
240
#4


dle_post 0 PRIMARY 1 id A 23687 NULL NULL BTREE
dle_post 1 autor 1 autor A 1184 NULL NULL BTREE
dle_post 1 alt_name 1 alt_name A 23687 NULL NULL BTREE
dle_post 1 category 1 category A 229 NULL NULL BTREE
dle_post 1 approve 1 approve A 2 NULL NULL BTREE
dle_post 1 allow_main 1 allow_main A 2 NULL NULL BTREE
dle_post 1 date 1 date A 23687 NULL NULL BTREE
dle_post 1 symbol 1 symbol A 1 NULL NULL BTREE
dle_post 1 comm_num 1 comm_num A 187 NULL NULL BTREE
dle_post 1 tags 1 tags A 51 NULL NULL BTREE
dle_post 1 approve_main 1 approve A 2 NULL NULL BTREE
dle_post 1 approve_main 2 allow_main A 4 NULL NULL BTREE
dle_post 1 fixed_date 1 fixed A 2 NULL NULL BTREE
dle_post 1 fixed_date 2 date A 23687 NULL NULL BTREE
dle_post 1 short_story 1 short_story NULL 1 NULL NULL FULLTEXT
dle_post 1 short_story 2 full_story NULL 1 NULL NULL FULLTEXT
dle_post 1 short_story 3 xfields NULL 1 NULL NULL FULLTEXT
dle_post 1 short_story 4 title NULL 1 NULL NULL FULLTEXT

dle_comments	0	PRIMARY	1	id	A	294624	NULL	NULL	BTREE	
dle_comments 1 user_id 1 user_id A NULL NULL NULL BTREE
dle_comments 1 post_id 1 post_id A NULL NULL NULL BTREE
dle_comments 1 approve 1 approve A NULL NULL NULL BTREE
dle_comments 1 comtime 1 date A NULL NULL NULL BTREE
dle_comments 1 approve_id 1 approve A NULL NULL NULL BTREE
dle_comments 1 approve_id 2 id A NULL NULL NULL BTREE
dle_comments 1 ng_photo_id 1 ng_photo_id A NULL NULL NULL YES BTREE
dle_comments 1 approve_deleted 1 approve A NULL NULL NULL BTREE
dle_comments 1 approve_deleted 2 is_deleted A NULL NULL NULL BTREE
dle_comments 1 is_deleted 1 is_deleted A NULL NULL NULL BTREE
dle_comments 1 static_id 1 static_id A NULL NULL NULL YES BTREE
dle_comments 1 event_id 1 event_id A NULL NULL NULL YES BTREE
dle_comments 1 deleted_photo_id 1 is_deleted A NULL NULL NULL BTREE
dle_comments 1 deleted_photo_id 2 photo_id A NULL NULL NULL YES BTREE
dle_comments 1 text 1 text NULL NULL NULL NULL FULLTEXT

dle_users	0	PRIMARY	1	user_id	A	13351	NULL	NULL	BTREE	
dle_users 0 name 1 name A 13351 NULL NULL BTREE
dle_users 0 email 1 email A 13351 NULL NULL BTREE


---------- Добавлено 14.01.2015 в 18:53 ----------

Вставил результаты

SHOW INDEX FROM dle_post;

SHOW INDEX FROM dle_comments;

SHOW INDEX FROM dle_users;

---------- Добавлено 14.01.2015 в 18:54 ----------

Ladycharm:
Устанавливаете бесплатную замечательную программу HeidiSQL - это типа phpmyadmin, но в сто раз круче (я даже не поленилась и donation автору отправила).

Получаете отменный user frendly GUIвизуальный доступ к своей БД, к котором можно добавить/удалить индексы, отладить любые SQL-запросы, и посмотреть время их выполнения, импортировать и экспортировать базы, смотреть статистику.

Вбиваете свой запрос туда и отлаживаете его прямо на ваших реальных таблицах. Смотрите explain запроса - какие индексы использует mysql при запросе, создаются ли временные таблицы, ...


PS: Иногда "select from select ..." работает быстрее чем объединение таблиц по join. Но это надо по экспериментировать на реальных таблицах.

PPS: HeidiSQL подключается к БД удалённо, надо чтобы у хостера был открыт наружу порт 3306. И уровень доступа к бд был не localhost(принимать подключения только внутри сервера), а %(с любого IP) или указан конкретный IP

PPPS: Select-ами - не накосячишь, а с запросами delete from table или drop db/drop table - аккуратнее, можно снести всё за 5 сек.

:)

про explain и прочие вещи в курсе.

Вопрос не в жтом, вопрос в том как оптимизировать запрос который в стартовом посте указан :)

---------- Добавлено 14.01.2015 в 18:57 ----------

Результат explain запроса

id	select_type	table	type	possible_keys	key	key_len	ref	rows	Extra
1 SIMPLE dle_comments ref approve,approve_id,approve_deleted,is_deleted,deleted_photo_id approve_id 1 const 285889 Using where
1 SIMPLE dle_post eq_ref PRIMARY,approve,approve_main PRIMARY 4 ladakz_dbnew.dle_comments.post_id 1
1 SIMPLE dle_users eq_ref PRIMARY PRIMARY 3 ladakz_dbnew.dle_comments.user_id 1
bukachuk
На сайте с 07.09.2008
Offline
97
#5

Запрос нормальный, индексы нужные уже есть. 285889 это не так много, Сколько по времени выполняется запрос?

imbalance
На сайте с 03.03.2007
Offline
240
#6

время выполнения от 0.5 до 10 секунд :(

bukachuk
На сайте с 07.09.2008
Offline
97
#7

А если просто запрос без JOIN-ов сделать, долго будет выбирать?

Попробуйте убрать сначала один потом другой JOIN из запроса, посмотреть что получиться только без кеширования типа SELECT SQL_NO_CACHE id, name FROM customer;

siv1987
На сайте с 02.04.2009
Offline
427
#8
imbalance:
ORDER BY id desc LIMIT 272010,10

В этом ваша проблема. Умные люди давно уже придумали сначала отсортировать первичный ключ, потом джоином выбирать остальные записи (на форуме не раз уже обсуждалось эта тема).

Ваш запрос будет выглядеть примерно так:

SELECT c.*, p.*, u.* FROM dle_comments c

INNER JOIN (SELECT id FROM dle_comments WHERE approve=1 AND is_deleted=0 ORDER BY id desc LIMIT 272010,10) z ON z.id=c.id
LEFT JOIN dle_post p ON (c.post_id=p.id AND p.approve=1)
LEFT JOIN dle_users u ON c.user_id=u.user_id
imbalance
На сайте с 03.03.2007
Offline
240
#9
siv1987:
В этом ваша проблема. Умные люди давно уже придумали сначала отсортировать первичный ключ, потом джоином выбирать остальные записи.

Ваш запрос будет выглядеть примерно так:

SELECT c.*, p.*, u.* FROM dle_comments c

INNER JOIN (SELECT id FROM dle_comments WHERE approve=1 AND is_deleted=0 ORDER BY id desc LIMIT 272010,10) z ON z.id=c.id
LEFT JOIN dle_post p ON (c.post_id=p.id AND p.approve=1)
LEFT JOIN dle_users u ON c.user_id=u.user_id

Спасибо большое!

imbalance
На сайте с 03.03.2007
Offline
240
#10

Благодарю, запрос переделал, стал работать быстрее, хотя все равно, далеко до идеала...

Возник еще вопрос, что посоветуете со следующим запросом?


SELECT comments.id as comid, comments.is_deleted as is_deleted,comments.date as comtime, comments.is_register, comments.user_id, comments.static_id as static_id, comments.text, comments.post_id, comments.autor, static.id, static.name as alt_name, static.descr as title, static.metakeys
FROM dle_comments as comments, dle_static as static
where static.id=comments.static_id and is_deleted=0
12

Авторизуйтесь или зарегистрируйтесь, чтобы оставить комментарий