Оператор MERGE для формирования таблицы отчетности - PullRequest
0 голосов
/ 25 июня 2019

Не могу решить задачу.Нам нужно создать таблицу отчетности о работниках и их командировках.Существует заполненная таблица FUNCT_TASK, в которой указаны имя сотрудника, кратный стране поездки и количество поездок в эту страну.Существует также изначально пустая таблица REPORT_TASK, столбцы которой называются именами сотрудников.Полный сценарий представлен ниже.

    CREATE TABLE FUNCT_TASK (
            PERSON VARCHAR2(100), 
            COUNTRY VARCHAR2(30), 
            REPEAT_NUM NUMBER(3)
        );
    CREATE TABLE REPORT_TASK
        (NAME1 VARCHAR2(30),
        NAME2 VARCHAR2(30),
        NAME3 VARCHAR2(30));

    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','BY',2);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','CN',2);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','BE',2);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','RU',2);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','AU',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','AR',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','DK',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name1','EG',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name2','BY',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name2','CN',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name2','UK',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name2','AU',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name2','RU',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name2','DK',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','IT',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','IL',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','BY',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','DE',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','IN',2);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','JP',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','RU',3);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','CN',1);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','BE',2);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','EG',6);
    Insert into FUNCT_TASK_RESULTS (PERSON,COUNTRY,REPEAT_NUM) values ('name3','CA',1);

    COMMIT;

It is necessary to insert / update the data in the REPORT_TASK table so that the result will be presented in the form:

    -----------------------
    name1     name2   name3
    -----------------------
    AR*1      AU*1    BE*2
    AU*1      BY*1    BY*1
    BE*2      CN*1    CA*1
    BY*2      DK*1    CN*1
    CN*2      RU*1    DE*1
    DK*1      UK*1    EG*6
    EG*1      null    IL*1
    RU*2      null    IN*2
    null      null    IT*1
    null      null    JP*1
    null      null    RU*3

В зависимости от условия задачи при решении необходимо использовать оператор MERGE (PIVOT невозможен).

1 Ответ

0 голосов
/ 25 июня 2019

Вы можете использовать row_number() для генерации данных:

select max(case when person = 'name1' then country || '*' || repeat_num end),
       max(case when person = 'name2' then country || '*' || repeat_num end),
       max(case when person = 'name3' then country || '*' || repeat_num end)
from (select t.*, row_number() over (partition by person order by person) as seqnum
      from t
     ) t
group by seqnum
order by seqnum;

Вы можете вставить это в таблицу, добавив перед оператором insert into report_task (name1, name2, name3).

...