powered by simpleCommunicator - 2.0.53     © 2025 Programmizd 02
Форумы / PostgreSQL [игнор отключен] [закрыт для гостей] / MERGE with DELETE option
6 сообщений из 6, страница 1 из 1
MERGE with DELETE option
    #39947456
Sintetik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Есть задача переписать запрос из базы которая поддерживает сабдж в постгрес который его не поддерживает.
Если бы без DELETE можно было бы использовать INSERT ON CONFLICT, но тут так

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

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
create table myTab (pid numeric, sales numeric, status varchar(6));
create table myTab2 (pid numeric, sales numeric, status varchar(6));
truncate table myTab;
truncate table myTab2;
insert into myTab2 values(1,12,'CURR');
insert into myTab2 values(2,13,'NEW' );
insert into myTab2 values(3,15,'CURR');
insert into myTab  values(2,24,'CURR');
insert into myTab  values(3, 0,'OBS' );
insert into myTab  values(4,42,'CURR');

WITH 
del as(
        delete from mytab2 m2
        using mytab m
        where m2.pid=m.pid and m2.sales<m.sales
        RETURNING m2.*
),
upd as (
   update mytab2 m 
   set sales=m.sales+d.sales, 
       status=d.status 
   from del d 
   where m.pid=d.pid
   RETURNING m.*
),
ins as (
    select pid, 
           sales,
           'NEW' 
    from mytab
    where pid not in (select pid from mytab2)
)
insert into mytab2
    select *
    from ins;
select * from myTab2;
...
Рейтинг: 0 / 0
MERGE with DELETE option
    #39947956
Guzya
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Поправьте если не прав, на выходе скрипта получите вставку двух строк (2,24,'CURR'), (4,42,'CURR') в myTab2 и все.
Не понятно:
- зачем truncate для только что созданных таблиц
- блок upd вроде ни чего не делает, поскольку сравнение идет по pid удаленной строки. Т.е. в del строку с таким pid удалили и пытаетесь её же обновить
в upd.

Если не прав, покажите какой результат на выходе получаете.
...
Рейтинг: 0 / 0
MERGE with DELETE option
    #39948373
Sintetik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Guzya
Поправьте если не прав, на выходе скрипта получите вставку двух строк (2,24,'CURR'), (4,42,'CURR') в myTab2 и все.
Не понятно:
- зачем truncate для только что созданных таблиц
- блок upd вроде ни чего не делает, поскольку сравнение идет по pid удаленной строки. Т.е. в del строку с таким pid удалили и пытаетесь её же обновить
в upd.

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

в этом и проблема/успех, что все куски отрабатывают, даже если не вызываются явно
транкейт просто для удобства отладки чтобы не дропать
исходно
Код: sql
1.
2.
3.
4.
pid	sales	status
1	12	CURR
2	13	NEW
3	15	CURR


результат
удалили ID=2
обновили ID=3
вставили ID=4 при этом учлось что ID=2 и 3 было в первоначальной таблице
Код: sql
1.
2.
3.
4.
5.
pid	sales	status
pid	sales	status
1	12	CURR
3	15	CURR
4	42	NEW
...
Рейтинг: 0 / 0
MERGE with DELETE option
    #39948443
Guzya
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
7.8.2. Изменение данных в WITH


Вложенные операторы в WITH выполняются одновременно друг с другом и с основным запросом. Таким образом, порядок, в котором операторы в WITH будут фактически изменять данные, непредсказуем. Все эти операторы выполняются с одним снимком данных (см. Главу 13), так что они не могут «видеть», как каждый из них меняет целевые таблицы.
...
Рейтинг: 0 / 0
MERGE with DELETE option
    #39948449
Sintetik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
из-за того что так подобрались данные
insert into myTab values(3, 0,'OBS' );

принял работу скрипта за правильную, а то у меня уже мозг закипать стал, ну как так то?
исправил исходные данные
insert into myTab values(3, 1,'OBS' );

Код: sql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
WITH 
del as(
        delete from mytab2 m2
        using mytab m
        where m2.pid=m.pid and m2.sales<m.sales
        RETURNING m2.*
),
upd as (
   update mytab2 m2 
   set sales=m2.sales+m.sales, 
       status=m.status 
   from mytab m--, del d 
   where m2.pid=m.pid and m2.pid not in (select pid from del)
   RETURNING m2.*
),
ins as (
    select pid, 
           sales,
           'NEW' 
    from mytab
    where pid not in (select pid from mytab2) and pid not in (select pid from upd)
)
insert into mytab2
    select *
    from ins;



теперь видно, что апдейт проходит 15+1=16
Код: sql
1.
2.
3.
4.
pid	sales	status
1	12	CURR
3	16	OBS
4	42	NEW
...
Рейтинг: 0 / 0
MERGE with DELETE option
    #39948451
Sintetik
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Guzya
7.8.2. Изменение данных в WITH


Вложенные операторы в WITH выполняются одновременно друг с другом и с основным запросом. Таким образом, порядок, в котором операторы в WITH будут фактически изменять данные, непредсказуем. Все эти операторы выполняются с одним снимком данных (см. Главу 13), так что они не могут «видеть», как каждый из них меняет целевые таблицы.

именно поэтому используется явно RETURNING
...
Рейтинг: 0 / 0
6 сообщений из 6, страница 1 из 1
Форумы / PostgreSQL [игнор отключен] [закрыт для гостей] / MERGE with DELETE option
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]