Първата ви грешка изглежда проста. Според втория параметър на crosstab()
функция, 'Dubai'
трябва да дойде като първи град (сортирани по град). Подробности:
Неочакваните стойности за totalsales
и totalamount
представляват стойности от първия ред за всяко name
група. „Допълнителните“ колони се третират така. Подробности:
За да получите суми на name
, стартирайте прозоречни функции върху вашите сборни функции. Подробности:
select * from crosstab (
'select name
,sum(count(*)) OVER (PARTITION BY name)
,sum(sum(price)) OVER (PARTITION BY name)
,city
,count(city)
from products
group by name,city
order by name,city
'
-- ,'select distinct city from products order by 1' -- replaced
,$$SELECT unnest('{Dubai,London,Melborun
,Moscow,Munich,Shunghai}'::varchar[])$$
) AS tb (
name varchar(20), TotalSales bigint, TotalAmount bigint
,Dubai bigint
,London bigint
,Melborun bigint
,Moscow bigint
,Munich bigint
,Shunghai bigint
);
Още по-добре, осигурете статичен набор като 2-ри параметър. Изходните колони са твърдо кодирани, може да е ненадеждно да се генерират динамично колони с данни. Ако добавите друг ред с нов град, това ще се счупи.
По този начин можете също да подредите колоните си както искате. Просто поддържайте изходните колони и втория параметър в синхрон.