ускорение рекурсивных запросов / циклический просмотр значений - PullRequest
1 голос
/ 17 апреля 2020

Предположим, что таблица со структурой, подобной этой:

create table tab1
(
id int,
valid_from timestamp
)

Мне нужно построить запрос таким образом, чтобы в случае наличия дублирования по паре (id, valid_from), например,

id    valid_from
1     2000-01-01 12:00:00
1     2000-01-01 12:00:00

затем одну секунду необходимо добавить к последующим строкам в столбце valid_from. Например, если есть три повторяющихся строки, результат должен быть следующим:

id    valid_from
1     2000-01-01 12:00:00
1     2000-01-01 12:00:01
1     2000-01-01 12:00:02

Попытка выполнить рекурсивный запрос cte, но, поскольку в некоторых случаях существует большое количество повторяющихся значений (для текущего набора данных около 160 для некоторых случаев (id, valid_from)) это действительно медленно. Спасибо

Ответы [ 2 ]

0 голосов
/ 17 апреля 2020

Если «следующая секунда» не занята, то:

WITH TAB (id, valid_from) AS 
(
VALUES
  (1, TIMESTAMP('2000-01-01 12:00:00'))
, (1, TIMESTAMP('2000-01-01 12:00:00'))
, (1, TIMESTAMP('2000-01-01 12:00:00'))

, (2, TIMESTAMP('2000-01-01 12:00:00'))
, (2, TIMESTAMP('2000-01-01 12:00:01'))
, (2, TIMESTAMP('2000-01-01 12:00:01'))
)
SELECT ID, VALID_FROM
, VALID_FROM + (ROWNUMBER() OVER (PARTITION BY ID, VALID_FROM) - 1) SECOND AS VALID_FROM2
FROM TAB
ORDER BY ID, VALID_FROM2;

Результат:

|ID         |VALID_FROM                |VALID_FROM2               |
|-----------|--------------------------|--------------------------|
|1          |2000-01-01-12.00.00.000000|2000-01-01-12.00.00.000000|
|1          |2000-01-01-12.00.00.000000|2000-01-01-12.00.01.000000|
|1          |2000-01-01-12.00.00.000000|2000-01-01-12.00.02.000000|
|2          |2000-01-01-12.00.00.000000|2000-01-01-12.00.00.000000|
|2          |2000-01-01-12.00.01.000000|2000-01-01-12.00.01.000000|
|2          |2000-01-01-12.00.01.000000|2000-01-01-12.00.02.000000|
0 голосов
/ 17 апреля 2020

Вы можете использовать оконные функции:

select id,
       valid_from + (row_number() over (partition by id order by valid_from) - 1) second
from t;
...