используйте MySQL SUM () в предложении WHERE

предположим, у меня есть эта таблица

id | cash 
1    200
2    301
3    101
4    700

и я хочу вернуть первую строку, в которой сумма всех предыдущих денежных средств превышает определенное значение:

Так, например, если я хочу вернуть первую строку, в которой сумма всех предыдущих денежных средств больше 500, должна вернуться в строку 3

Как это сделать с помощью оператора mysql?

используя WHERE SUM(cash) > 500 не работает

4 ответов


вы можете использовать агрегаты только для сравнения в предложении HAVING:

GROUP BY ...
  HAVING SUM(cash) > 500

на HAVING предложения требует определения группы by пункт

чтобы получить первую строку, где сумма наличных превышает определенного значения, использовать:

SELECT y.id, y.cash
  FROM (SELECT t.id,
               t.cash,
               (SELECT SUM(x.cash)
                  FROM TABLE x
                 WHERE x.id <= t.id) AS running_total
         FROM TABLE t
     ORDER BY t.id) y
 WHERE y.running_total > 500
ORDER BY y.id
   LIMIT 1

поскольку агрегатная функция возникает в подзапросе, на псевдоним столбца для нее можно ссылаться в предложении WHERE.


Не проверял, но я думаю, что это будет близко?

SELECT m1.id
FROM mytable m1
INNER JOIN mytable m2 ON m1.id < m2.id
GROUP BY m1.id
HAVING SUM(m1.cash) > 500
ORDER BY m1.id
LIMIT 1,2

идея состоит в том, чтобы суммировать все предыдущие строки, получить только те, где сумма предыдущих строк > 500, затем пропустить одну и вернуть следующую.


В общем, условие WHERE пункт SQL-запроса может ссылаться только на одну строку. Контекст a WHERE предложение оценивается до того, как любой заказ был определен ORDER BY предложение, и нет неявного порядка для таблицы СУБД.

вы можете использовать производную таблицу для присоединения каждой строки к группе строк с меньшим id значение и произведите сумму каждой группы сумм. Затем проверьте, где сумма соответствует критерий.

CREATE TABLE MyTable ( id INT PRIMARY KEY, cash INT );

INSERT INTO MyTable (id, cash) VALUES
  (1, 200), (2, 301), (3, 101), (4, 700);

SELECT s.*
FROM (
  SELECT t.id, SUM(prev.cash) AS cash_sum
  FROM MyTable t JOIN MyTable prev ON (t.id > prev.id)
  GROUP BY t.id) AS s
WHERE s.cash_sum >= 500
ORDER BY s.id
LIMIT 1;

выход:

+----+----------+
| id | cash_sum |
+----+----------+
|  3 |      501 |
+----+----------+

при использовании агрегатных функций для фильтрации необходимо использовать оператор HAVING.

SELECT *
FROM tblMoney
HAVING Sum(CASH) > 500