对别名字段的Postgres整理

时间:2015-07-01 10:43:30

标签: postgresql internationalization collation

我有下表:

CREATE TABLE public_bodies
  ("id" int, "name" varchar(46))
;

INSERT INTO public_bodies
  ("id", "name")
VALUES
  (1, 'Ytre Helgeland District Psychiatric Centre'),
  (2, 'Åfjord Municipality'),
  (3, 'Østfold Hospital')
;

我想运行此查询:

SELECT public_bodies.id, public_bodies.name AS display_name
FROM public_bodies
ORDER BY display_name COLLATE "en_US";

但是我收到了这个错误:

ERROR:  column "display_name" does not exist
LINE 3: ORDER BY display_name COLLATE "en_US";
                 ^

按表名排序可以正常工作:

SELECT public_bodies.id, public_bodies.name AS display_name
FROM public_bodies
ORDER BY public_bodies.name COLLATE "en_US";

--  id |        display_name
-- ----+--------------------------------------------
--   2 | Åfjord Municipality
--   3 | Østfold Hospital
--   1 | Ytre Helgeland District Psychiatric Centre

对别名进行排序也可以:

SELECT public_bodies.id, public_bodies.name AS display_name
FROM public_bodies
ORDER BY display_name;

--  id |        display_name
-- ----+--------------------------------------------
--   2 | Åfjord Municipality
--   3 | Østfold Hospital
--   1 | Ytre Helgeland District Psychiatric Centre

在分配别名之前应用COLLATE有效,但我不明白为什么这与ORDER_BY之后的整理不同。

SELECT public_bodies.id, public_bodies.name COLLATE "en_US" AS display_name
FROM public_bodies
ORDER BY display_name;

--  id |        display_name
-- ----+--------------------------------------------
--   2 | Åfjord Municipality
--   3 | Østfold Hospital
--   1 | Ytre Helgeland District Psychiatric Centre

Postgres版本:

SELECT version();
                                               version
-------------------------------------------------------------------------------------------------------------
 PostgreSQL 9.1.12 on x86_64-unknown-linux-gnu, compiled by gcc (Ubuntu/Linaro 4.6.3-1ubuntu5) 4.6.3, 64-bit

我在SQL小提琴上得到了相同的结果(Postgres 9.3)。

为什么Postgres不能对别名字段进行整理?

1 个答案:

答案 0 :(得分:0)

这是语言定义的方式。 COLLATE条款适用于表达式,此案例不具备资格。

通过"表达式",我的意思是一些运算符,函数,变量标识符,文字等的集合,它们组合起来产生一个输出值。换句话说,一般类别的价值生产"事物"允许在SELECT列表中显示为函数参数,VALUES字段定义,依此类推。

COLLATE子句可以附加到表达式,表达式可以出现在ORDER BY列表中,但它不是唯一允许的内容一个ORDER BY列表;您还可以包含names or positions of output columns,但解析器会将这些视为一个独特的案例。

需要区别对待的原因是查询表达式时查询的输出字段标识符不在scope中;这就是ORDER BY display_name || 'x'之类的内容与column "display_name" does not exist一起回来的原因。要解决此问题,在尝试进行表达式求值之前,会将ORDER BY列表中的裸字段名称与输出列表进行比较,但因此,在此上下文中不会接受比纯字段名称更复杂的内容(并且包括附加的COLLATE条款。