Группировать или объединять несколько столбцов по нескольким критериям

Мне нужно сделать то, что, как я думал, будет простым SQL-запросом... но я застрял, решая, как их можно сгруппировать:

    <p>I've got the below table:</p>
Company    | Airport    |     Type
------------------------------------------
SP1        | AP1        |     ST1             
SP1        | AP1        |     ST2        
SP1        | AP1        |     ST3        
SP1        | AP2        |     ST1         
SP1        | AP2        |     ST2        
SP1        | AP2        |     ST3 
SP1        | AP3        |     ST1 
SP1        | AP3        |     ST2 
SP1        | AP4        |     ST1 
SP1        | AP4        |     ST2 
SP1        | AP4        |     ST3 
SP1        | AP4        |     ST4 

Я хочу сгруппировать AP и ST следующим образом, чтобы желаемый результат был таким:

(ДЕЛО 1)

SP         | AP             |     ST
------------------------------------------
SP1        | AP1, AP2, AP4  |     ST1, ST2, ST3
SP1        | AP3            |     ST1, ST2        
SP1        | AP4            |     ST4    

Есть предположения? Очень ценю!

Обновить

Как уже отмечалось, есть еще одна альтернатива результату:

(СЛУЧАЙ 2)

SP         | AP             |     ST
------------------------------------------
SP1        | AP1, AP2       |     ST1, ST2, ST3
SP1        | AP3            |     ST1, ST2        
SP1        | AP4            |     ST1, ST2, ST3, ST4    

Я также добавил заголовки к столбцам, чтобы дать немного больше контекста. Идея заключается в том, чтобы иметь возможность группировать связанные элементы. Я доволен любым из двух результатов, надеюсь, обоими вариантами, если это возможно.


person user3510607    schedule 08.04.2014    source источник
comment
возможный дубликат эквивалентен массиву PostgreSQL()/ функции array_to_string() в Oracle 9i, которые также ссылаются на oracle-base.com/articles/misc/string-aggregation-techniques.php   -  person Glenn    schedule 08.04.2014
comment
можете ли вы объяснить ожидаемый набор результатов (или исправить его)?   -  person Rob van Wijk    schedule 08.04.2014
comment
Почему AP4 появляется в первой выходной строке вместо ST1, ST2, ST3, ST4 в третьей строке?   -  person Darius X.    schedule 08.04.2014
comment
AP4 — это особый случай (СЛУЧАЙ 1), поскольку он содержит все элементы группы AP1 и AP2 (т. е. ST1, ST2, ST3) плюс дополнительный элемент ST4, который должен отображаться в отдельной строке, поскольку он не является частью группы AP1 и AP2. Надеюсь, это проясняет ситуацию!   -  person user3510607    schedule 08.04.2014


Ответы (1)


Не описывается, почему AP4/ST4 является особым случаем, но предположим, что вы пытаетесь сгруппировать по 3 последовательных элемента в ST для каждого (sp,ap):

SQL> with t (SP, AP, ST) as (
  2  select 'SP1','AP1','ST1' from dual union all
  3  select 'SP1','AP1','ST2' from dual union all
  4  select 'SP1','AP1','ST3' from dual union all
  5  select 'SP1','AP2','ST1' from dual union all
  6  select 'SP1','AP2','ST2' from dual union all
  7  select 'SP1','AP2','ST3' from dual union all
  8  select 'SP1','AP3','ST1' from dual union all
  9  select 'SP1','AP3','ST2' from dual union all
 10  select 'SP1','AP4','ST1' from dual union all
 11  select 'SP1','AP4','ST2' from dual union all
 12  select 'SP1','AP4','ST3' from dual union all
 13  select 'SP1','AP4','ST4' from dual
 14  )
 15  select sp, listagg(ap,',') within group (order by ap) lstap, lstst
 16  from (
 17  select sp, ap, listagg(st,',') within group (order by st) lstst from (
 18  select sp, ap, st, ceil((row_number() over(partition by sp, ap order by st))/3) grp
 19  from t
 20  )
 21  group by sp, ap, grp
 22  )
 23  group by sp, lstst
 24  order by 1,2,3
 25  /

SP  LSTAP                     LSTST                                             
--- ------------------------- -------------------------                         
SP1 AP1,AP2,AP4               ST1,ST2,ST3                                       
SP1 AP3                       ST1,ST2                                           
SP1 AP4                       ST4  

P.S. Для альтернативного вывода результата:

SQL> with t (SP, AP, ST) as (
  2  select 'SP1','AP1','ST1' from dual union all
  3  select 'SP1','AP1','ST2' from dual union all
  4  select 'SP1','AP1','ST3' from dual union all
  5  select 'SP1','AP2','ST1' from dual union all
  6  select 'SP1','AP2','ST2' from dual union all
  7  select 'SP1','AP2','ST3' from dual union all
  8  select 'SP1','AP3','ST1' from dual union all
  9  select 'SP1','AP3','ST2' from dual union all
 10  select 'SP1','AP4','ST1' from dual union all
 11  select 'SP1','AP4','ST2' from dual union all
 12  select 'SP1','AP4','ST3' from dual union all
 13  select 'SP1','AP4','ST4' from dual
 14  )
 15  select sp, listagg(ap,',') within group (order by ap) lstap, lstst
 16  from (
 17  select sp, ap, listagg(st,',') within group (order by st) lstst from (
 18  select sp, ap, st
 19  from t
 20  )
 21  group by sp, ap
 22  )
 23  group by sp, lstst
 24  order by 1,2,3
 25  /

SP  LSTAP                     LSTST                                             
--- ------------------------- -------------------------                         
SP1 AP1,AP2                   ST1,ST2,ST3                                       
SP1 AP3                       ST1,ST2                                           
SP1 AP4                       ST1,ST2,ST3,ST4  
person Dmitry Nikiforov    schedule 08.04.2014
comment
Спасибо, Дмитрий, прежде чем я попытаюсь переварить ваше решение ... относительно вашего комментария, предположим, что вы пытаетесь сгруппировать 3 последовательных элемента в ST. Будет ли ваш SQL поддерживать произвольное количество ST? В моем случае: ST1, ST2... STn, и то же самое для AP1, AP2.. APn. - person user3510607; 08.04.2014
comment
В приведенном выше запросе я группирую по 3 последовательным элементам в ST. Я также предполагаю, что пробелов нет (например, нет случая ST1, ST2, [без ST3] ST4). Если эти условия выполняются, запрос должен работать. P.S. Я только что видел вашу альтернативу - это должно сработать для вас, если длина вывода listagg не превышает 4000 байт - это предел для символьных функций SQL в 11G. - person Dmitry Nikiforov; 08.04.2014
comment
Хорошо, если забыть о СЛУЧАЕ 1 выше (который я сейчас считаю слишком сложным, и окончательная группировка будет в значительной степени зависеть от исходного порядка элементов), есть ли у вас какие-либо мысли о гораздо более простом СЛУЧАЕ 2, который группирует только абсолютно идентичные последовательности? ? - person user3510607; 08.04.2014
comment
Я только что добавил пример - см., пожалуйста, комментарий выше. - person Dmitry Nikiforov; 08.04.2014
comment
Идеально! Это решение, которое я искал, большое спасибо Дмитрий! - person user3510607; 08.04.2014