PostgreSQL GROUP BY LOWER() 不工作

Posted

技术标签:

【中文标题】PostgreSQL GROUP BY LOWER() 不工作【英文标题】:PostgreSQL GROUP BY LOWER() not working 【发布时间】:2015-04-24 20:10:35 【问题描述】:

我正在尝试在 PostgreSQL 9.4.1 中使用 GROUP BY,但没有取得预期的成功。

the web 上有 several folks 声称这应该有效,但我无法得到相同的结果。我想要的只是一个不区分大小写的GROUP BY,但每次我添加LOWER() 它都会抱怨:

错误:列“people.fn”必须出现在 GROUP BY 子句中,否则 在聚合函数中使用

CREATE DATABASE TEST;
CREATE TABLE people (id INTEGER, fn TEXT, ln TEXT); /* ID, firstname, lastname */

INSERT INTO people (id, fn, ln) VALUES(1,'Mike','f');
INSERT INTO people (id, fn, ln) VALUES(2,'adam','b');
INSERT INTO people (id, fn, ln) VALUES(3,'bill','b');
INSERT INTO people (id, fn, ln) VALUES(4,'Bill','r');
INSERT INTO people (id, fn, ln) VALUES(5,'mike','d');
INSERT INTO people (id, fn, ln) VALUES(6,'mike','c');
INSERT INTO people (id, fn, ln) VALUES(7,'Mike','T');

SELECT fn FROM people GROUP BY LOWER(fn);  /* will not run */
SELECT fn FROM people GROUP BY fn;  /* runs, but not what I want */

这是我得到的:

adam
mike
Mike
bill
Bill

这就是我想要的:

Mike
adam
bill

显然,我缺少一些东西。不,我不能在将数据放入数据库时​​对其进行清理。我应该阅读什么来理解这一点?

【问题讨论】:

在 SELECT 中也使用 LOWER。 【参考方案1】:

一般来说,如果你想在聚合查询中选择一些东西,你必须按这个“东西”来分组。在你的情况下,你可以通过选择lower(fn)来获得你想要的结果:

select lower(fn)
from people
group by lower(fn)

幸运的是,PostgreSQL 允许您按别名进行分组,因此您不必重复 lower(fn) 两次:

select lower(fn) as lfn
from people
group by lfn

sql fiddle demo

正如@okaram 在 cmets 中提到的,如果您不需要任何其他的聚合,您最好使用distinct

select distinct lower(fn)
from people

【讨论】:

太棒了。我知道这会很简单。谢谢罗曼。 这是因为同一组中可能有多个值,SQL无法决定您想要哪个; Mike mike MIKE 都会映射到 mike,所以同一个组 (mike) 会有多个值,这是不可能发生的 你可能想要 DISTINCT 而不是 GROUP BY 在这里,如 SELECT DISTINCT LOWER(fn) FROM people

以上是关于PostgreSQL GROUP BY LOWER() 不工作的主要内容,如果未能解决你的问题,请参考以下文章