Глядя на various answers for ORDER BY with CASE like this one, я вижу, что то, что я вынужден делать в этом устаревшем приложении, вероятно, является экспертным методом; однако он слишком медленный, когда строки меньше тривиальных (строки из 100 000 или более загрузок страниц составляют 10 секунд).mysql ORDER BY with CASE - слишком медленно, быстрее?
Обратите внимание, что исходный запрос предназначен для решения, по-видимому, распространенной проблемы, когда аналитику запроса нужны даты, которые отсортированы в пустом порядке, как они обычно сортируются. В этом случае datefirstprinted
должен опускаться, но все записи, которые не печатаются, должны быть заполнены в верхней части списка.
Оригинал Запрос решает эту проблему, но суть вопроса в том, чтобы избежать попадания filesort
производительности, который поставляется с производный столбец notprintedyet
.
Оригинал Запрос
SELECT SQL_NO_CACHE
id, daterun, datefirstprinted,
case datefirstprinted when "0000-00-00 00:00:00" then 1 else 0 end as notprintedyet
FROM
patientrecords
WHERE
dateuploaded <> '0000-00-00 00:00:00'
ORDER BY
notprintedyet desc, /* ordered via alias */
datefirstprinted desc
LIMIT 10;
время 1.52s
я обнаружил, что не сортировать по псевдониму notprintedyet
экономит немного:
немного быстрее Запрос
SELECT SQL_NO_CACHE
id, daterun, datefirstprinted,
case datefirstprinted when "0000-00-00 00:00:00" then 1 else 0 end as notprintedyet
FROM
patientrecords
WHERE
dateuploaded <> '0000-00-00 00:00:00'
ORDER BY
datefirstprinted = "0000-00-00 00:00:00" desc, /* directly ordered */
datefirstprinted
LIMIT 10;
время 1.37s
Оптимальная скорость, но отсутствует необходимый сортировкой пустой даты S первый
SELECT SQL_NO_CACHE
id, daterun, datefirstprinted,
case datefirstprinted when "0000-00-00 00:00:00" then 1 else 0 end as notprintedyet
FROM
patientrecords
WHERE
dateuploaded <> '0000-00-00 00:00:00'
ORDER BY
datefirstprinted /* not ordered properly */
LIMIT 10;
время 0.48s
Я попытался с помощью view
create view notprinted_patientrecords as (
SELECT id, daterun, datefirstprinted, case datefirstprinted when "0000-00-00 00:00:00" then 1 else 0 end notprintedyet
FROM patientrecords
WHERE dateuploaded <> '0000-00-00 00:00:00'
);
, к сожалению, когда я бегу explain
explain select * from notprinted_patientrecords order by notprintedyet desc limit 10;
это показывает, что я все еще использую filesort
и принимает1.51sака не экономии на всех
Будет ли он быстрее, если datefirstprinted по умолчанию NULL?
может быть, но в этом унаследованного приложения, которые могут принести больше вреда, чем 5 секунд дополнительных в время загрузки страницы
Что еще мы могли бы попробовать? Хранимые процедуры? Функции?
ОБНОВЛЕНИЕ
Как предложил @strawberry - ORDER BY ДЕЛУ
...
ORDER BY
case datefirstprinted when "0000-00-00 00:00:00" then 1 else 0 end, datefirstprinted
LIMIT 10;
время 1.52s
по просьбе @ e4c5, то explain
выход:
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: patientrecords
type: range
possible_keys: dateuploaded,uploads_report
key: dateuploaded
key_len: 5
ref: NULL
rows: 299095
Extra: Using index condition; Using filesort
за исключением не упорядочено должным образом, который имеет следующую дисперсию
rows: 10
Extra: Using where
создать таблицу заявление
*************************** 1. row ***************************
Table: patientrecords
Create Table: CREATE TABLE `patientrecords` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`datecreated` datetime NOT NULL,
`dateuploaded` datetime NOT NULL,
`daterun` datetime NOT NULL,
`datebilled` datetime NOT NULL,
`datefirstprinted` datetime NOT NULL,
`datelastprinted` datetime NOT NULL,
`client` varchar(5) NOT NULL,
PRIMARY KEY (`id`),
KEY `dateuploaded` (`dateuploaded`),
KEY `daterun` (`daterun`),
KEY `uploads_report` (`dateuploaded`,`client`),
KEY `datefirstprinted` (`datefirstprinted`),
KEY `datelastprinted` (`datelastprinted`)
)
Вы пытаетесь ускорить запрос, который занимает одну или две миллисекунды? Просто не имеет смысла. –
@gordonlinoff - не знаю, почему я поставил «мс» во времена ... это в секундах. thx - обновлено. – WEBjuju
Вы попробовали заказать по 'case ...' – Strawberry