select
t1.NOMER, min(t2.NOMER)
from BLANC t1 join BLANC t2 on t1.NOMER <= t2.NOMER
where
not exists (select NOMER,BLANC.BSO from BLANC t3 where t1.NOMER - 1 = t3.NOMER)
and
not exists (select NOMER,BLANC.BSO from BLANC t4 where t2.NOMER + 1 = t4.NOMER)
group by t1.NOMER
SQL> create table ranges as
2 select 1 num, 'Grp1' grp from dual union
3 select 2 num, 'Grp1' grp from dual union
4 select 3 num, 'Grp1' grp from dual union
5 select 5 num, 'Grp1' grp from dual union
6 select 6 num, 'Grp2' grp from dual union
7 select 7 num, 'Grp2' grp from dual union
8 select 8 num, 'Grp1' grp from dual ;
Table created
SQL>
SQL> select grp, min (num), max (num)
2 from (
3 select grp, num, num - rownum grp#
4 from (select * from ranges order by grp, num))
5 group by grp, grp# ;
GRP MIN(NUM) MAX(NUM)
---------- ---------- ----------
Grp1 1 3
Grp1 5 5
Grp1 8 8
Grp2 6 7
SQL>
Re[2]: Поиск непрерывных диапазонов
От:
Аноним
Дата:
14.10.05 18:21
Оценка:
Здравствуйте, Softwarer
Разобрался с трудом. Вроде то что мне нужно.
Большое вам спасибо!
Re: Поиск непрерывных диапазонов
От:
Аноним
Дата:
14.10.05 18:41
Оценка:
Гм на Firebird это не работает...
это случайино не для MSSQL?
Нет, это не для MSSQL. Как это адаптировать для FB — не в курсе, но почти уверен, что удастся применить ту же идею.
Re[3]: Поиск непрерывных диапазонов
От:
Аноним
Дата:
14.10.05 19:15
Оценка:
Хорошо. для меня на данном этапе такой запрос сложноват
просто я теоретически пока не понял что он делает.
Сижу ищу по этой теме чтонибудь.
Наверное вы правы просто мне не хватило знаний адаптировать.
Буду разбираться. Вам большое спасибо!!!
Идея этого запроса очень проста — я пользуюсь тем фактом, что в непрерывном интервале (отсортированном по порядку) число в следующей строке возрастает на единицу и номер строки также возрастает на единицу; соответственно их разность остается неизменной (инвариантом). При любом нарушении последовательности эта разность увеличивается; таким образом, сгруппировав по разности, получаем по группе для каждого интервала — и берем min/max для этой группы. Ну и в Вашем случае — дополнительно суем группировку по BSO.
Re[5]: Поиск непрерывных диапазонов
От:
Аноним
Дата:
14.10.05 19:40
Оценка:
Ага.. Стало понятно.
Теперь получилось с некоторыми видоизменениями.
Еще раз вам спасибо Александр.
Re: Поиск непрерывных диапазонов
От:
Аноним
Дата:
15.10.05 08:45
Оценка:
Еще раз возвращаюсь к этой теме.
Как оказалось я этот код протестировал на FB 2.0 а это как известно еще alpha версия.
В ней работают derived запросы. А в 1.5.x такой возможности нету.
То есть всё таки можно ли как нибудь передалать мой ниже приведенный запрос в такую
форму о которой я написал?
select
t1.NOMER, min(t2.NOMER)
from BLANC t1 join BLANC t2 on t1.NOMER <= t2.NOMER
where
not exists (select NOMER,BLANC.BSO from BLANC t3 where t1.NOMER - 1 = t3.NOMER)
and
not exists (select NOMER,BLANC.BSO from BLANC t4 where t2.NOMER + 1 = t4.NOMER)
group by t1.NOMER
Здравствуйте, Аноним, Вы писали:
А>То есть всё таки можно ли как нибудь передалать мой ниже приведенный запрос в такую форму о которой я написал?
Не вижу препятствий. По идее, MIN(BSO) должен сработать не хуже, чем MIN(t2.NOMER). Единственно, подозреваю, стоит включить BSO в условия join-ов — иначе непонятно что выдавать в случае выборки
Здравствуйте, Аноним, Вы писали:
А>То есть всё таки можно ли как нибудь передалать мой ниже приведенный запрос в такую форму о которой я написал?
Другой вопрос, что я не уверен в оправданности такой переделки — Ваш запрос, подозреваю, будет исполняться очень неэффективно (это, конечно, зависит от оптимизатора, но — подозреваю). Может быть, лучше будет возвращать нужные данные из хранимки — там можно обработать входной поток в один проход.
Re[4]: Поиск непрерывных диапазонов
От:
Аноним
Дата:
16.10.05 06:26
Оценка:
MIN(BSO) Работает не так как надо. Выводит всё также, как и в случае просто BSO. Тут дело может быть в Group By?
Насчет еффективности ничего не могу сказать... Может у вас есть апробированный алгоритм по типу этого только не derived с запросами?
Я сам тоже попытаюсь через хранимую процедуру всё сделать.
Здравствуйте, Аноним, Вы писали:
А>MIN(BSO) Работает не так как надо. Выводит всё также, как и в случае просто BSO.
Хм. А чем Вас не устраивает этот результат?
А>Насчет еффективности ничего не могу сказать... Может у вас есть апробированный алгоритм по типу этого только не derived с запросами?
Для процедуры алгоритм тривиальный — взять выборку с сортировкой по возрастанию номеров (возможно, BSO и номеров), идти по ней и проверять условие непрерывности диапазона; когда нарушается — выплевывать очередную строку.
Здравствуйте!
Решил наконец то
И с ХП и так.
Ну с ХП понятно. Но просто с запросом ступил оказалось надо так
select
t1.NOMER, min(t2.NOMER), t1.BSO
from BLANC t1 join BLANC t2 on t1.NOMER <= t2.NOMER
where
not exists (select NOMER,BLANC.BSO from BLANC t3 where t1.NOMER - 1 = t3.NOMER)
and
not exists (select NOMER,BLANC.BSO from BLANC t4 where t2.NOMER + 1 = t4.NOMER)
group by t1.NOMER, t1.BSO