SQL查询ORDER BY问题 - 似乎没有按预期排序

时间:2015-04-30 13:55:16

标签: mysql

我有一个按预期返回值的查询,但是ORDER BY似乎在最后一列(totalPointsSum)上是一个别名列。

下面显示了这些数据的外观示例。显然我想要6200第一,400秒和50第三个按totalPointsSum排序 - 任何关于我做错的想法?​​

+---------+----------+----------------+
| user_id | username | totalPointsSum |
| 5555555 |    bob   |      6200      |
| 6666666 |   geoff  |       50       |
| 7777777 |    lee   |      400       |
+---------|----------|----------------+

我的表格结构如下:

myusers(user_id, username);
organisations(organisation_id, organisation_name);
codes(redeemed_code_id, user_id, unique_code, date_redeemed, school_points, inactive);

我的查询如下..

        SELECT
        t.*, (
            SELECT
                COALESCE (SUM(x.school_points), "0")
            FROM
                codes x
            WHERE
                x.user_id = t.user_id
            AND x.school_points > 0
            AND x.inactive = 0
            AND (
                x.date_redeemed >= 1393286400
                OR x.date_redeemed = 0
            )
        ) AS totalPointsSum
    FROM
        `myusers` `t`
    INNER JOIN organisation o ON (
        t.organisation_id = o.organisation_id
    )
    WHERE
        o.organisation_id = 25679
    ORDER BY totalPointsSum desc

P.S我很快就会添加一个方便的

4 个答案:

答案 0 :(得分:2)

问题在于这一行:

COALESCE (SUM(x.school_points), "0")

字符串"0"强制内部查询(totalPointsSum)计算的值的类型为字符串。因此,ORDER BY totalPointsSum desc对字符串"6200""50""400"进行排序并做得很好。

"0"(字符串)更改为0(数字),查询将按您的意愿运行。

答案 1 :(得分:1)

看来你的内部SELECT的返回值被视为字符串而不是整数。

尝试添加零(这应该强制它被视为数字):

 ORDER BY totalPointsSum+0 DESC

旁注:

您可以验证school_points实际上是INT字段。如果不是,只需将其更改为INT字段即可。

答案 2 :(得分:1)

或者,从COALESCE函数中的0周围删除双引号。这将消除正在发生的隐式数据转换,并允许表达式为数字。

COALESCE(SUM(x.school_points),  0  )
                               ^ ^ 

您也可以使用MySQL IFNULL函数

IFNULL(SUM(x.school_points),0)

无论哪种方式,这将是传递给外部查询的数字列,因此ORDER BY将把它作为数字而不是字符串来处理。

对两个不同数据类型的表达式(例如数字和字符串)使用COALESCE时,会有一个隐式转换,因此返回的列是单个数据类型。

您在原始陈述中发生的是隐式数据转换,基本上等同于显式表达:

 COALESCE(CAST( SUM(x.school_points) AS VARCHAR(50)), '0')
          ^^^^^                      ^^^^^^^^^^^^^^^

如果删除零附近的引号,则会将字符串文字中的零更改为数字文字。这意味着SUM()不必转换为字符类型。

答案 3 :(得分:0)

请尝试ORDER BY LENGTH(totalPointsSum)desc,totalPointsSum desc;

这样可以模拟自然顺序。