Стандартное решение SQL выглядит примерно так:
select listagg(id, ',') within group (order by id) as ids,
listagg(name, ',') within group (order by id) as names
from (select t.*, row_number() over (order by id) as seqnum
from t
) t
group by cast( (seqnum - 1) / 3 as int);
Я думаю, что это будет работать как есть в Oracle. В MySQL вам нужно изменить listagg()
на group_concat()
(и использовать MySQL 8+), а в Postgres вам нужно изменить listagg()
на string_agg()
.
И вы в значительной степени не можете сделать это в Sybase.
Ой, подождите, есть другой способ:
select concat( (case when seqnum % 3 = 1 then concat(id, ';') else '' end),
(case when seqnum % 3 = 2 then concat(id, ';') else '' end),
(case when seqnum % 3 = 0 then concat(id, ';') else '' end)
) as ids,
concat( (case when seqnum % 3 = 1 then concat(name, ';') else '' end),
(case when seqnum % 3 = 2 then concat(name, ';') else '' end),
(case when seqnum % 3 = 0 then concat(name, ';') else '' end)
) as name
from (select t.*, row_number() over (order by id) as seqnum
from t
) t
group by cast( (seqnum - 1) / 3 as int);
Конечно, Sybase не поддерживает concat()
, поэтому вы должны использовать +
. И это дает ;
для разделителя, а не ,
, но это довольно близко.