Заказ по / лимит выполнения в SQL

В сети уже много веток, я просто пытаюсь понять некоторые нюансы, которые меня запутали!

Цитирование ссылка на документ

If you combine LIMIT row_count with ORDER BY, MySQL stops sorting as soon as it has found the first row_count rows of the sorted result, rather than sorting the entire result. If ordering is done by using an index, this is very fast.

и SO поток

It will order first, then get the first 20. A database will also process anything in the WHERE clause before ORDER BY.

Взяв тот же запрос из вопроса:

SELECT article
FROM table1
ORDER BY publish_date
LIMIT 20

допустим, таблица имеет 2000 строк, из которых ожидается, что query вернет 20 строк, теперь взгляд на ссылка на mysql....stops sorting as soon as it has found the first row_count rows.... сбивает меня с толку, поскольку я нахожу это немного двусмысленным !!

Почему написано stops sorting? не применяется ли предложение limit к уже отсортированным данным, возвращаемым через предложение order by (предполагая, что это столбец non-indexed), или я неправильно понимаю, и SQL сначала выполняет limit, а затем сортирует !! ??

Освоение архитектуры микросервисов с Laravel: Лучшие практики, преимущества и советы для разработчиков
Освоение архитектуры микросервисов с Laravel: Лучшие практики, преимущества и советы для разработчиков
В последние годы архитектура микросервисов приобрела популярность как способ построения масштабируемых и гибких приложений. Laravel , популярный PHP...
Как построить CRUD-приложение в Laravel
Как построить CRUD-приложение в Laravel
Laravel - это популярный PHP-фреймворк, который позволяет быстро и легко создавать веб-приложения. Одной из наиболее распространенных задач в...
Освоение PHP и управление базами данных: Создание собственной СУБД - часть II
Освоение PHP и управление базами данных: Создание собственной СУБД - часть II
В предыдущем посте мы создали функциональность вставки и чтения для нашей динамической СУБД. В этом посте мы собираемся реализовать функции обновления...
Документирование API с помощью Swagger на Springboot
Документирование API с помощью Swagger на Springboot
В предыдущей статье мы уже узнали, как создать Rest API с помощью Springboot и MySql .
Роли и разрешения пользователей без пакета Laravel 9
Роли и разрешения пользователей без пакета Laravel 9
Этот пост изначально был опубликован на techsolutionstuff.com .
Как установить LAMP Stack - Security 5/5 на виртуальную машину Azure Linux VM
Как установить LAMP Stack - Security 5/5 на виртуальную машину Azure Linux VM
В предыдущей статье мы завершили установку базы данных, для тех, кто не знает.
0
0
1 257
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Оптимизация, упомянутая в документации, обычно работает только при наличии индекса в столбце publish_date. Значения хранятся в индексе по порядку, поэтому механизм просто выполняет итерацию по индексу столбца, извлекая связанные строки, пока не будет извлечено 20 строк.

Если столбец не проиндексирован, движку обычно необходимо извлечь все строки, отсортировать их, а затем вернуть первые 20 из них.

Также полезно понять, как это взаимодействует с условиями WHERE. Предположим, запрос:

SELECT article
FROM table1
WHERE last_read_date > '2018-11-01'
ORDER BY publish_date
LIMIT 20

Если publish_date проиндексирован, а last_read_date нет, он просканирует индекс publish_date по порядку, проверит связанный last_read_date на соответствие условию и добавит article к набору результатов, если тест завершится успешно. Когда в наборе результатов будет 20 строк, он остановится и вернет его.

Если last_read_date проиндексирован, а publish_date - нет, он будет использовать индекс last_read_date для поиска подмножества всех строк, удовлетворяющих условию. Затем он отсортирует эти строки, используя столбец publish_date, и вернет из него первые 20 строк.

Если ни один столбец не проиндексирован, он выполнит полное сканирование таблицы для проверки last_read_date, отсортирует все строки, соответствующие условию, и вернет первые 20 строк этого.

Привет, Бармар, спасибо за объяснение. Пара сомнений: 1. В зависимости от столбца indexed, mysql может фактически вернуть мне другой набор строк во всех трех случаях, которые вы описали? 2. If publish_date is indexed and last_read_date is not -> поскольку по умолчанию order by находится в ASC, этот запрос фактически не вернет мне самый старый article, поскольку критерии фильтрации указаны в order by, а не в предложении where? (означает, что в этом случае возвращается самый старый publish date в сочетании с last read !!!)

NoobEditor 09.12.2018 04:41

Если у вас есть несколько строк с одинаковой датой публикации, так что точка отсечения 20 строк заканчивается в группе строк с одинаковой датой публикации, вы можете получить разные результаты своих запросов. Например, вы публикуете 6 статей в день, и все они читаются. Вы всегда будете получать те же 18 из первых 3 дней, но вы получите только 2 из четвертого дня, и какие 2 вы получите, может отличаться в зависимости от того, какой вариант запроса вы используете. Если бы у вас были разные publish_date в каждой строке, вы всегда получите те же 20, независимо от того, какой у них индекс. Индекс меняет способ получения данных mysql, а не то, что вы получаете.

DancingFool 10.12.2018 01:33

@NoobEditor Если нет повторяющихся значений publish_date, вы должны получить те же результаты. Это просто оптимизации производительности, они не меняют смысла запроса.

Barmar 10.12.2018 05:51

если есть дубликаты и критериям соответствует более 20 строк, то непредсказуемо, какие 20 он выберет, и различные оптимизации могут привести к выбору разных значений.

Barmar 10.12.2018 05:53

MySQL stops sorting as soon as it has found the first row_count rows of the sorted result, rather than sorting the entire result

На самом деле это очень разумная оптимизация в mysql. Если вы используете limit для возврата 20 строк, а mysql знает, что он их уже нашел, то зачем mysql (или вам) заботиться о том, как именно сортируются остальные записи? Это не имеет значения, поэтому mysql перестает сортировать остальные строки.

Если упорядочение выполняется по индексированному столбцу, то mysql может довольно быстро определить, нашел ли он первые n записей.

Другие вопросы по теме