5

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

简化示例:

SET @a = 1;

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

结果:

+------+------+
| 总和 | @a |
+------+------+
| 2 | 1 |
+------+------+

我希望@a 在这里是 2。

其他示例:

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

现在它是NULL,因为@b 在查询之前没有被设置。

似乎该变量没有被 SUM 函数的结果覆盖。有没有什么办法解决这一问题?

4

2 回答 2

7

文档中所述

作为一般规则,您永远不应为用户变量赋值并在同一语句中读取该值。您可能会得到预期的结果,但这不能保证。涉及用户变量的表达式的求值顺序是未定义的,并且可能会根据给定语句中包含的元素而改变;此外,不保证此顺序在 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
于 2012-05-11T13:32:38.690 回答
1

它连接到表达式评估。在您的情况下,您可以使用子查询 -

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

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

更多信息 -用户定义的变量

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

于 2012-05-11T13:34:04.043 回答