MySQL用户变量和SUM函数

时间:2012-05-11 13:08:18

标签: mysql

我正在尝试在SELECT查询中进行一些计算,使用用户变量来执行此操作。这很好用,直到我开始使用像SUM这样的函数来从连接表中收集数据。

简化示例:

SET @a = 1;

SELECT @a := SUM(1 + 1) AS sum, @a

结果:

+------+------+
| sum  | @a   |
+------+------+
|    2 |    1 |
+------+------+

我希望@a在这里是2。

其他例子:

SELECT @b := SUM(1 + 1) AS sum, @b;
+------+------+
| sum  | @b   |
+------+------+
|    2 | NULL |
+------+------+

现在它为NULL,因为在查询之前@b未设置。

似乎该变量不会被SUM函数的结果覆盖。有什么方法可以解决这个问题吗?

2 个答案:

答案 0 :(得分:5)

如上所述in the documentation

作为一般规则,您永远不应将值分配给用户变量并读取同一语句中的值。您可能会得到您期望的结果,但这不能保证。涉及用户变量的表达式的评估顺序是未定义的,可能会根据给定语句中包含的元素进行更改;此外,MySQL服务器版本之间的订单不保证相同。在SELECT @a, @a:=@a+1, ...中,您可能认为MySQL将首先评估@a,然后再进行一次分配。但是,更改语句(例如,通过添加GROUP BYHAVINGORDER BY子句)可能会导致MySQL选择具有不同评估顺序的执行计划。

到你问题的第二部分。您可以在这样的查询中初始化@variable(首先评估子查询):

SELECT @b := SUM(1 + 1) AS sum, @b FROM (SELECT @b:=0) b

答案 1 :(得分:1)

与表达评价有关。在您的情况下,您可以使用子查询 -

SET @a = 1;
SELECT sum, @a FROM
  (SELECT @a := SUM(1 + 1) AS sum, @a) t

+------+------+
| sum  | @a   |
+------+------+
|    2 |    2 |
+------+------+

更多信息 - User-Defined Variables

  

作为一般规则,您不应该为用户变量赋值   并在同一语句中读取值。你可能会得到   你期望的结果,但这不能保证。的顺序   涉及用户变量的表达式的评估是未定义的   可能会根据给定声明中包含的元素进行更改;   另外,这个顺序不保证是相同的   MySQL服务器的版本。在SELECT @ a,@ a:= @ a + 1,...,你可以   认为MySQL会首先评估@a然后做一个任务   第二。但是,更改语句(例如,通过添加   GROUP BY,HAVING或ORDER BY子句可能导致MySQL选择一个   执行计划具有不同的评估顺序。