我在 CREATE TABLE 语句中有以下行:
field1_id bigint DEFAULT nextval('table1_field1_id_seq'::regclass) NOT NULL,
上面的regclass是什么意思?是否必须添加 ::regclass
?
注意:我看过 Postgresql 文档 link它讲述了 regclass
,但无法理解。
最佳答案
不,在调用像 nextval
这样接受 regclass
参数的函数时,您不需要转换为 regclass
,因为有一个从 text
到 regclass
的隐式转换。在某些其他情况下,可能需要显式转换为 regclass
。
解释:
::regclass
是一个转换,如 ::integer
。
regclass
是一种“神奇”的数据类型;它实际上是 oid
的别名,或“对象标识符”。参见 Object identifier types在文档中。转换为 regclass
是说“这是关系的名称,请将其转换为该关系的 oid”的快捷方式。转换为 regclass
知道 search_path
,这与直接查询 pg_class
关系的 oid
不同,因此转换为 regclass不完全等同于子查询 pg_class
。
表是关系。序列和 View 也是如此。因此,您也可以通过转换为 regclass 来获取 View 或序列的 oid。
为 text
定义了隐式转换为 regclass
,因此如果您省略显式转换并且您正在调用接受 regclass
的函数> Actor 是自动完成的。因此您不需要在 nextval
调用中需要它。
还有其他地方你可以。例如,您不能将 text
直接与 oid
进行比较;所以你可以这样做:
regress=> select * from pg_class where oid = 'table1'::regclass;
但不是这个:
regress=> select * from pg_class where oid = 'table1';
ERROR: invalid input syntax for type oid: "table1"
LINE 1: select * from pg_class where oid = 'table1';
只是为了好玩,我尝试编写一个查询来执行转换为 regclass
的等效操作。不要使用它,它主要是为了好玩,并试图演示实际发生的事情。除非你真的对 Pg 的胆量如何工作感兴趣,否则你可以停止阅读这里。
据我了解,'sequence_name'::regclass::oid
大致等同于以下查询:
WITH sp(sp_ord, sp_schema) AS (
SELECT
generate_series(1, array_length(current_schemas('t'),1)),
unnest(current_schemas('t'))
)
SELECT c.oid
FROM pg_class c INNER JOIN pg_namespace n ON (c.relnamespace = n.oid)
INNER JOIN sp ON (n.nspname = sp.sp_schema)
WHERE c.relname = 'sequence_name'
ORDER BY sp.sp_ord
LIMIT 1;
除了它更短更快。参见 System information functions对于 current_schemas(...)
等的定义
换句话说:
- 获取一个 ab 数组,列出我们有权访问的所有模式,并将每个条目与其在数组中的位置的序号配对
- 在
pg_class
中搜索与匹配名称的关系,并将每个关系与其命名空间(架构)相关联 - 按照模式在
search_path
中出现的顺序对剩余关系列表进行排序 - 并选择第一场比赛
关于postgresql - regclass在Postgresql中是什么意思,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13289107/