Сумма (случай, когда) приводит к нескольким строкам выбора

У меня есть огромная таблица заказов клиентов, и я хочу запустить один запрос, чтобы просмотреть список заказов по месяцам за последние 13 месяцев по «user_id». То, что у меня есть сейчас (ниже), работает, но вместо того, чтобы перечислять только одну строку для каждого user_id, он перечисляет одну строку для каждого заказа, который имеет user_id. Пример: один пользователь имеет 42 общих заказа за всю свою жизнь с нами, поэтому он перечисляет его user_id в 42 строках, и в каждой строке есть только один платеж. Обычно я просто добавляю это в сводную таблицу в Excel, но я превышаю ограничение в миллион строк, поэтому мне нужно, чтобы оно было правильным и не имело нулевого успеха. Я хотел бы, чтобы чтение выглядело так:

идентификатор_пользователя | июль_12 | авг_12 |

123456 | 150.00 | 150.00 |

Не этот:

идентификатор_пользователя | июль_12 | авг_12 |

123456 | 0.00 | 150.00 |

123456 | 150.00 | 0.00 |

пр. еще 40 рядов

SELECT ui.user_id, 
SUM(CASE WHEN date_part('year', o.time_stamp) = 2012 AND date_part('month', o.time_stamp) = 07 THEN o.amount ELSE 0 END) jul_12,
SUM(CASE WHEN date_part('year', o.time_stamp) = 2012 AND date_part('month', o.time_stamp) = 08 THEN o.amount ELSE 0 END) aug_12,
FROM orders o JOIN users_info ui ON ui.user_id = o.user_id
WHERE user_id = '123456'
GROUP BY ui.user_id, o.time_stamp;

person greenpowerade    schedule 07.08.2013    source источник


Ответы (1)


Попробуйте что-то вроде:

SELECT ui.user_id, 
SUM(CASE WHEN date_part('year', o.time_stamp) = 2012 AND date_part('month', o.time_stamp) = 07 THEN o.amount ELSE 0 END) jul_12,
SUM(CASE WHEN date_part('year', o.time_stamp) = 2012 AND date_part('month', o.time_stamp) = 08 THEN o.amount ELSE 0 END) aug_12,
FROM orders o JOIN users_info ui ON ui.user_id = o.user_id
WHERE user_id = '123456'
GROUP BY ui.user_id;

Вы получали одну строку для каждого заказа, потому что вы группировали по o.time_stamp, а временные метки для каждого заказа разные.

Более короткая версия запроса:

SELECT ui.user_id, 
SUM(CASE WHEN date_trunc('month', o.time_stamp) = to_date('2012 07','YYYY MM') THEN o.amount END) jul_12,
SUM(CASE WHEN date_trunc('month', o.time_stamp) = to_date('2012 08','YYYY MM') THEN o.amount END) aug_12,
FROM orders o 
JOIN users_info ui ON ui.user_id = o.user_id
WHERE ui.user_id = '123456'
GROUP BY ui.user_id;
person Ihor Romanchenko    schedule 07.08.2013
comment
Что, если бы я хотел пересечь годы? Так что если эти два вместо 07 июля и 08 августа, где 2012 12 декабря и 2013 01 января. Моя цель - запустить его в течение длительного периода времени, чтобы увидеть тенденции порядка. Спасибо! - person greenpowerade; 07.08.2013
comment
Вы все еще можете использовать CASE, который вы использовали — я переместил фильтр года на WHERE, чтобы сократить запрос и ускорить его. - person Ihor Romanchenko; 07.08.2013
comment
Duh - это плохо для меня, я думаю. Спасибо! Есть ли другой способ приблизиться к нескольким столбцам? Или, если я хочу получить 24 месяца, у меня будет 24 строки, по одной на каждый месяц? - person greenpowerade; 08.08.2013
comment
@greenpowerade Вы можете попробовать this. Но лучшим решением было бы получить данные в простой таблице id, month, sum и повернуть их на стороне клиента с помощью какого-либо языка программирования. - person Ihor Romanchenko; 08.08.2013