如何在PostgreSQL中以编程方式查找继承的表?

如何在PostgreSQL中以编程方式查找继承的表?,第1张

概述我有一个PostgreSQL 8.3数据库,其中正在使用表继承.我想获得所有表的列表及其模式名称,该名称是使用查询从基表继承的.我们有什么方法可以使用PGSQL获得这个吗? 由于你使用的是旧版本的PostgreSQL,你可能不得不使用PL / PgSQL函数来处理>的继承深度. 1.在现代PostgreSQL(甚至8.4)上,您将使用递归公用表表达式(WITH RECURSIVE). pg_cat 我有一个Postgresql 8.3数据库,其中正在使用表继承.我想获得所有表的列表及其模式名称,该名称是使用查询从基表继承的.我们有什么方法可以使用PGsql获得这个吗? 由于你使用的是旧版本的Postgresql,你可能不得不使用PL / Pgsql函数来处理>的继承深度. 1.在现代Postgresql(甚至8.4)上,您将使用递归公用表表达式(WITH RECURSIVE).

pg_catalog.pg_inherits表是关键.鉴于:

create table pp( );     -- The parent we'll search forCREATE table notpp(); -- Another root for multiple inheritancecreate table cc( ) inherits (pp); -- a 1st level child of ppcreate table dd( ) inherits (cc,notpp); -- a 2nd level child of pp that also inherits aacreate table notshown( ) inherits (notpp); -- table that inherits only notppcreate table ccdd () inherits (cc,dd) -- inheritance is a graph not a tree; join node

正确的结果将找到cc,dd和ccdd,但找不到notpp或notshown.

单深度查询是:

SELECT pg_namespace.nspname,pg_class.relname FROM pg_catalog.pg_inherits   INNER JOIN pg_catalog.pg_class ON (pg_inherits.inhrelID = pg_class.oID)   INNER JOIN pg_catalog.pg_namespace ON (pg_class.relnamespace = pg_namespace.oID) WHERE inhparent = 'pp'::regclass;

……但这只会找到cc.

对于多深度继承(即tableC继承tableB继承tableA),您必须通过递归CTE或PL / Pgsql中的循环来扩展它,使用最后一个循环的子节点作为下一个循环的父节点.

更新:这是一个8.3兼容版本,应该递归地查找直接或间接从给定父级继承的所有表.如果使用多重继承,它应该在树的任何位置找到任何具有目标表作为其父节点之一的表.

CREATE OR REPLACE FUNCTION find_children(oID) RETURNS SetoF oID as $$SELECT i.inhrelID FROM pg_catalog.pg_inherits i WHERE i.inhparent = UNIONSELECT find_children(i.inhrelID) FROM pg_catalog.pg_inherits i WHERE i.inhparent = ;$$LANGUAGE 'sql' Stable;CREATE OR REPLACE FUNCTION find_children_of(parentoID IN regclass,schemaname OUT name,tablename OUT name) RETURNS SetoF record AS $$SELECT pg_namespace.nspname,pg_class.relname         FROM find_children() inh(inhrelID)           INNER JOIN pg_catalog.pg_class ON (inh.inhrelID = pg_class.oID)           INNER JOIN pg_catalog.pg_namespace ON (pg_class.relnamespace = pg_namespace.oID);$$LANGUAGE 'sql' Stable;

用法:

regress=# SELECT * FROM find_children_of('pp'::regclass); schemaname | tablename ------------+----------- public     | cc public     | dd public     | ccdd(3 rows)

这是递归CTE版本,如果您更新Pg将会起作用,但不适用于您当前的版本.这是更清洁的IMO.

WITH RECURSIVE inh AS (        SELECT i.inhrelID FROM pg_catalog.pg_inherits i WHERE inhparent = 'pp'::regclass        UNION        SELECT i.inhrelID FROM inh INNER JOIN pg_catalog.pg_inherits i ON (inh.inhrelID = i.inhparent))SELECT pg_namespace.nspname,pg_class.relname     FROM inh       INNER JOIN pg_catalog.pg_class ON (inh.inhrelID = pg_class.oID)       INNER JOIN pg_catalog.pg_namespace ON (pg_class.relnamespace = pg_namespace.oID);
总结

以上是内存溢出为你收集整理的如何在PostgreSQL中以编程方式查找继承的表?全部内容,希望文章能够帮你解决如何在PostgreSQL中以编程方式查找继承的表?所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/sjk/1181627.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-06-02
下一篇 2022-06-02

发表评论

登录后才能评论

评论列表(0条)

保存