ORDER BY别名不起作用

时间:2011-06-23 18:09:27

标签: sql postgresql group-by aggregate-functions

更新问题:

ERROR:  column "Fruits" does not exist

运行Postgres 7.4(是的,我们正在升级)

为什么我不能按列别名进行排序?想要在ORDER BY中使用“TypeOfFruits”,为什么?

SELECT (CASE
    WHEN tof."TypeOfFruits" = 'A' THEN 'Apple' 
    WHEN tof."TypeOfFruits" = 'P' THEN 'Pear' 
    WHEN tof."TypeOfFruits" = 'G' THEN 'Grapes' 
    ELSE 'Other' END) AS "Fruits",
    SUM(CASE WHEN r.order_date 
        BETWEEN DATE_TRUNC('DAY', LOCALTIMESTAMP) AND DATE_TRUNC('DAY', LOCALTIMESTAMP) + INTERVAL '1 DAY' 
        THEN 1 ELSE 0 END) AS daily, 
    SUM(CASE WHEN r.order_date 
        BETWEEN DATE_TRUNC('MONTH', LOCALTIMESTAMP) AND DATE_TRUNC('MONTH', LOCALTIMESTAMP) + INTERVAL '1 MONTH' 
        THEN 1 ELSE 0 END) AS monthly, 
    SUM(CASE WHEN r.order_date 
        BETWEEN DATE_TRUNC('YEAR', LOCALTIMESTAMP) AND DATE_TRUNC('YEAR', LOCALTIMESTAMP) + INTERVAL '1 YEAR' 
        THEN 1 ELSE 0 END) AS yearly, 
    SUM(CASE WHEN r.order_date >= '01-01-2011 00:00:00' THEN 1 ELSE 0 END) AS lifetime 
FROM reports AS r, "TypeOfFruits" AS tof 
WHERE r.id = tof."ID" 
GROUP BY "Fruits"
ORDER BY CASE 
    WHEN "Fruits" = 'Apple' THEN 1 
    WHEN "Fruits" = 'Pear' THEN 2 
    WHEN "Fruits" = 'Grapes' THEN 3 
    ELSE 4 
END

截至目前的结果

Fruits;daily;monthly;yearly;lifetime
"Apple";17;1174;3136;3136
"Pear";28;94;94;94
"Grapes";0;191;490;490
"Other";0;2;27;27
"Other";0;0;1;1
"Other";0;0;27;27
"Other";0;6;28;28
"Other";0;58;229;229
"Other";0;3;3;3
"Other";0;0;1;1

期望的结果将是具有“其他”总计的一行,因此总共四行 (x将是总数)

Fruits;daily;monthly;yearly;lifetime
"Apple";17;1174;3136;3136
"Pear";28;94;94;94
"Grapes";0;191;490;490
"Other";x;x;x;x

6 个答案:

答案 0 :(得分:7)

您可以使用ORDER BY 1按第一个字段排序,即“Fruits”。这同样适用于GROUP BY

<强>更新

对于订单而言,不是在case中执行order by,而是在......中创建一个新列。第二个位置:

(CASE 
    WHEN "Fruits" = 'Apple' THEN 1 
    WHEN "Fruits" = 'Pear' THEN 2 
    WHEN "Fruits" = 'Grapes' THEN 3 
    ELSE 4 ) as Order

然后在你ORDER BY 2

答案 1 :(得分:5)

可以在documentation

中找到原因
  

每个表达式[在ORDER BY列表中]可以是输出列(SELECT列表项)的名称或序号,也可以是由 input <形成的任意表达式/ em> - 列值。

(我的重点)

原因是旧版本的SQL标准(SQL-92)只允许按输出列名称或编号进行排序,而较新版本允许按任意表达式排序,但这些表达式是由输入列值组成的。 / p>

其他答案已经包含了适合您案例的各种解决方法。

答案 2 :(得分:2)

考虑这样的事情:

SELECT * FROM (SELECT (CASE
    WHEN tof."TypeOfFruits" = 'A' THEN 'Apple' 
    WHEN tof."TypeOfFruits" = 'P' THEN 'Pear' 
    WHEN tof."TypeOfFruits" = 'G' THEN 'Grapes' 
    ELSE 'Other' END) AS "Fruits", 
    (CASE 
    WHEN tof."TypeOfFruits" = 'A' THEN 1 
    WHEN tof."TypeOfFruits" = 'P' THEN 2 
    WHEN tof."TypeOfFruits" = 'G' THEN 3 
    ELSE 4 END) as NUM

        FROM ..... <rest of your query without group by and order by .....
    )

GROUP BY Fruits
ORDER BY NUM

答案 3 :(得分:1)

别名在订单后分配,因此您无法按顺序使用它。请改用:

(CASE
    WHEN tof."TypeOfFruits" = 'A' THEN 'Apple' 
    WHEN tof."TypeOfFruits" = 'P' THEN 'Pear' 
    WHEN tof."TypeOfFruits" = 'G' THEN 'Grapes' 
    ELSE 'Other' END)

答案 4 :(得分:0)

你可以尝试这样的事情......未经测试,但我也见过类似的问题 让我知道它是否有效......

SELECT "Fruits",
    SUM(CASE WHEN r.order_date 
        BETWEEN DATE_TRUNC('DAY', LOCALTIMESTAMP) AND DATE_TRUNC('DAY', LOCALTIMESTAMP) + INTERVAL '1 DAY' 
        THEN 1 ELSE 0 END) AS daily, 
    SUM(CASE WHEN r.order_date 
        BETWEEN DATE_TRUNC('MONTH', LOCALTIMESTAMP) AND DATE_TRUNC('MONTH', LOCALTIMESTAMP) + INTERVAL '1 MONTH' 
        THEN 1 ELSE 0 END) AS monthly, 
    SUM(CASE WHEN r.order_date 
        BETWEEN DATE_TRUNC('YEAR', LOCALTIMESTAMP) AND DATE_TRUNC('YEAR', LOCALTIMESTAMP) + INTERVAL '1 YEAR' 
        THEN 1 ELSE 0 END) AS yearly, 
    SUM(CASE WHEN r.order_date >= '01-01-2011 00:00:00' THEN 1 ELSE 0 END) AS lifetime 
FROM reports AS r
    ,(SELECT "ID",
             CASE
                WHEN tof."TypeOfFruits" = 'A' THEN 'Apple' 
                WHEN tof."TypeOfFruits" = 'P' THEN 'Pear' 
                WHEN tof."TypeOfFruits" = 'G' THEN 'Grapes' 
                ELSE 'Other'
             END AS "Fruits" FROM "TypeOfFruits" ) AS "tof"
WHERE r.id = tof."ID" 
GROUP BY "Fruits"
ORDER BY CASE 
    WHEN "Fruits" = 'Apple' THEN 1 
    WHEN "Fruits" = 'Pear' THEN 2 
    WHEN "Fruits" = 'Grapes' THEN 3 
    ELSE 4 
END

答案 5 :(得分:-1)

尝试使用反引号(`)而不是单/双引号来包装别名。

与MySQL有同样的问题;反引号解决了问题。