#mysql #sql
Вопрос:
За каждый месяц (кроме января) Я хотел бы найти разницу в количестве по сравнению с предыдущим месяцем.
У меня есть столик:
Месяц | Кол-во |
---|---|
Январь | 4 |
Февраль | 3 |
Март | 9 |
Апрель | 3 |
Май | 7 |
и я хотел бы вернуться:
Месяц | Разница |
---|---|
Февраль | -1 |
Март | 6 |
Апрель | -6 |
Май | 4 |
Я использую более старую версию MySQL, поэтому я не могу использовать для этого ОПЕРЕЖЕНИЕ/ЗАДЕРЖКУ.
Комментарии:
1. У вас в таблице всего 12 строк, по 1 на каждый месяц?
2. Да, но эти данные представляют собой сводку данных транзакции, которая содержит столбцы ID и Datetime. Задача состоит в том, чтобы подсчитать транзакции за месяц, а затем найти разницу между месяцами.
3. Опубликуйте свои фактические данные.
4. У вас всегда есть строка за любой предыдущий месяц или могут быть пробелы? Что следует делать, если есть пробел? У вас тоже есть колонка с годом?
Ответ №1:
SELECT t1.`Month`, COALESCE(t1.Qty - t2.Qty, 'Unknown') Difference
FROM table t1
LEFT JOIN table t2
ON STR_TO_DATE(CONCAT(t1.`Month`, ' 01 2021'), '%M %d %Y')
= STR_TO_DATE(CONCAT(t2.`Month`, ' 01 2021'), '%M %d %Y') INTERVAL 1 MONTH
Ответ №2:
Вы можете использовать коррелированный подзапрос, чтобы получить предыдущее значение. Если первый столбец действительно упорядочен, то вы можете использовать:
select t.*, (qty - prev_qty) as difference
from (select t.*,
(select t2.qty
from t t2
where t2.month < t.month
order by t2.month desc
limit 1
) as prev_qty
from t
) t
where prev_qty is not null;
Если вы действительно храните месяцы в виде строкового имени, то вам нужно преобразовать их во что-то упорядоченное:
select t.*, (qty - prev_qty) as difference
from (select t.*,
(select t2.qty
from t t2
where str_to_date(concat(t2.month, ' 1 2000', '%M %d %Y') < str_to_date(concat(t.month, ' 1 2000', '%M %d %Y')
order by str_to_date(concat(t2.month, ' 1 2000', '%M %d %Y') desc
limit 1
) as prev_qty
from t
) t
where prev_qty is not null;