#mysql #sql #sum #inner-join #full-outer-join
#mysql #sql #сумма #внутреннее соединение #полное внешнее соединение
Вопрос:
У меня есть таблица оборота с одной стороны, которая имеет :
Storeid Turnover myDate
| 1 | 1000 | 2020-01-01 |
| 1 | 200 | 2020-01-02 |
| 1 | 4000 | 2020-01-03 |
| 1 | 1000 | 2020-01-05 |
с другой стороны, у меня есть таблица с количеством транзакций:
Storeid Transactions myDate
| 1 | 20 | 2020-01-01 |
| 1 | 40 | 2020-01-03 |
| 1 | 20 | 2020-01-04 |
| 1 | 60 | 2020-01-05 |
Мне нужно вычислить сумму оборота и сумму транзакций за заданный диапазон дат. Однако у меня могут отсутствовать даты в любой из таблиц. Если я суммирую их по отдельности, я получаю правильный ответ для каждого, кроме любого вида внутреннего или левого соединения, и я получаю неполные ответы (как показано ниже):
select sum(Turnover), sum(transactions) from TurnoverTable
left join TransactionTable on TurnoverTable.storeid = TransactionTable.storeid and
TurnoverTable.myDate = TransactionTable.myDate where TurnoverTable.myDate >= '2020-01-01'
Это приведет к получению суммы для оборота в 6200 и для транзакций в 120 (20 отсутствует в дате 2020-01-04, поскольку эта дата недоступна в таблице оборота, поэтому объединение завершается ошибкой).
Есть ли способ запустить эти суммы, если не запускать 2 запроса select sum?
Высоко ценится.
Ответ №1:
В обеих таблицах отсутствуют даты, что исключает left join
решение. Концептуально, вы хотите full join
. В MySQL, где этот синтаксис не поддерживается, вы можете использовать union all
; остальное — просто агрегирование:
select sum(turnover) turnover, sum(transactions) transactions
from (
select mydate, turnover, 0 transactions
union all
select mydate, 0, transactions
) t
where mydate >= '2020-01-01'
Ответ №2:
Что касается такого рода статистики, вам не следует использовать JOIN. Потому что вы можете получить неправильные результаты из-за дублирования строк. Особенно, нам нужно объединить много таблиц на практике.
Поэтому я рекомендую использовать ОБЪЕДИНЕНИЕ следующим образом: Пожалуйста, включите предложение date where в ОБЪЕДИНЕНИЕ.
SELECT
Storeid,
SUM(Turnover),
SUM(Transactions)
FROM
(SELECT
Storeid,
myDate,
Turnover,
0 AS Transactions
FROM
turnovers
WHERE myDate BETWEEN '2020-01-01'
AND '2020-08-21'
UNION
ALL
SELECT
Storeid,
myDate,
0 AS Turnover,
Transactions
WHERE myDate BETWEEN '2020-01-01'
AND '2020-08-21'
FROM
Transactions) AS t
GROUP BY Storeid ;