Как посчитать сумы разных категорий за каждый день?

Здарова!

Есть таблица:
CREATE TABLE Table1
    ("user_id" int, "date" timestamp, "amount" int, "currency" varchar(3))
;
    
INSERT INTO Table1
    ("user_id", "date", "amount", "currency")
VALUES
    (1, '2016-03-28 00:00:00', 10, 'USD'),
    (1, '2016-03-28 00:00:00', 13, 'USD'),
    (1, '2016-03-28 00:00:00', 15, 'USD'),
    (1, '2016-03-28 00:00:00', 18, 'USD'),
    (1, '2016-03-28 00:00:00', 16, 'EUR'),
    (1, '2016-03-29 00:00:00', 10, 'EUR'),
    (1, '2016-03-29 00:00:00', 13, 'EUR'),
    (1, '2016-03-29 00:00:00', 15, 'USD'),
    (1, '2016-03-29 00:00:00', 18, 'USD'),
    (1, '2016-03-29 00:00:00', 16, 'USD'),
    (1, '2016-03-30 00:00:00', 11, 'USD'),
    (1, '2016-03-30 00:00:00', 12, 'EUR'),
    (1, '2016-03-30 00:00:00', 19, 'EUR'),
    (1, '2016-03-30 00:00:00', 17, 'EUR'),
    (1, '2016-03-30 00:00:00', 13, 'USD'),
    (1, '2016-03-30 00:00:00', 12, 'EUR'),
    (1, '2016-03-30 00:00:00', 16, 'EUR')
;


Нужно получить сумы по каждой валюте за каждый день. Что бы было похоже на:
user_id | date       | usd | eur
--------+------------+-----+-----
1       | 2016-03-28 | 56  | 16
--------+------------+-----+-----
1       | 2016-03-29 | 49  | 23
--------+------------+-----+-----
1       | 2016-03-30 | 24  | 76


Есть условие что валют может быть несколько, и их нельзя строго забить в запрос. Я вот понимаю что нужно выбрать какие валюты есть в таблице и потом сделать выборку по каждой валюте и суммировать. Но вот как записать это все в результат не понимаю.
  • Вопрос задан
  • 338 просмотров
Решения вопроса 1
Melkij
@Melkij
PostgreSQL DBA
Postgresql 9.4 и старше умеет более читаемый синтаксис из SQL:2003 взамен длинного CASE в примере nozzy
select 
user_id,
date,
SUM(amount) filter(where currency = 'USD') AS USD,
SUM(amount) filter(where currency = 'USD') AS EUR
FROM Table1
GROUP BY user_id, date


Список возможных валют вам придётся вписывать в запрос.
Либо дополнительно группировать по валюте и разгребать уже на приложении.
Ответ написан
Пригласить эксперта
Ответы на вопрос 2
NikitaTratorov
@NikitaTratorov
CTO
Если не обращать внимание на то, что Вы сфантазировали два новых столбца, то легко:
SELECT Table1.user_id,
       Table1.`date`,
       SUM(Table1.amount) as sum,
       Table1.currency
  FROM new_site.Table1 Table1
GROUP BY Table1.currency, Table1.`date`

А если Вам нужно генерировать столбцы, то увы, их нужно знать заранее и дописывать в запрос динамически:
SELECT 
Table1.user_id, 
Table1.`date`, 
(SELECT SUM(amount) FROM Table1 tbl2 WHERE tbl2.`date` = Table1.`date` AND tbl2.currency = 'USD') as USD,
(SELECT SUM(amount) FROM Table1 tbl2 WHERE tbl2.`date` = Table1.`date` AND tbl2.currency = 'EUR') as EUR
  FROM new_site.Table1 Table1
GROUP BY Table1.`date`
Ответ написан
Комментировать
@nozzy
Symfony, Laravel, SQL
select 
user_id,
date,
SUM(CASE WHEN currency = 'USD' THEN amount ELSE 0 END) AS USD,
SUM(CASE WHEN currency = 'EUR' THEN amount ELSE 0 END) AS EUR
FROM Table1 AS
GROUP BY user_id, date

или использовать IF:
SUM( IF(currency = 'USD', amount, 0) ) AS USD,
SUM( IF(currency = 'EUR', amount, 0) ) AS EUR
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы