Постраничная разбивка с Oracle.
Ни для кого не секрет, что Oracle - это труЪ =) Но когда я "проапгрэйдился" на проекте до него с MySQL, то я не нашел там привычного сердцу LIMIT 0, 20
и расстроился. Как же так. Самая лучшая БД, а такой полезной функции нет.
Разбираясь с ExtJS, где для грида мне эта постраничность и была нужна, я наткнулся на тред, где приводилось вменяемое решение для моей проблемы и с успехом его применял.
В приведенном решении меня не устраивало 3 вещи:
- Для подсчета строк надо делать отдельный запрос
- Глючит при хитрых
ORDER BY
- DBA сказал "мутная весчь этот rownum" =)
Решение было найдено довольно быстро. И оно было избавлено от всех 3х недостатков. Вместо "мутного" rownum была применена функция row_number(), которая дала нужный результат. Плюс доработав запрос, я получил в нем и колличество строк. Правда оно пишется в каждой строке ответа, но нам же оно нужно для постраничной разбивки, поэтому заботиться о количестве данных, передаваемых по сети не стоит. Вот готовый рецепт:
select * from (
select ROW_NUMBER() over(order by req.requests_date desc) as r,
count(tab.id) over() as total,
from table tab,
where tab.column = 'value'
) x
where x.r between '" . ($start + 1) . "' and '" . ($start + $limit) . "'
Ссылка на документацию по Oracle может внести дополнительную ясность, от себя добавлю лишь, что в over()
пишем все ORDER BY
, $start
и $limit
это с чего начинать(начинаем с 0) и на чем остановиться (передается количество записей на страницу). count()
должен применяться на unique поле (что характерно ;). Вот, в принципе, всё. Если остаются вопросы или предложения по оптимизации — прошу в комменты.
Комментариев нет:
Отправить комментарий