FROM 子句中的 Postgres 子查询

Posted

技术标签:

【中文标题】FROM 子句中的 Postgres 子查询【英文标题】:Postgres subquery in FROM clause 【发布时间】:2019-03-22 22:21:39 【问题描述】:

在 Postgres 中,我在 FROM 子句中使用了子查询,但我真的不知道如何获得我想要的结果。假设我有 2 张桌子,tableNameRegister(idNum integer, tableName text)mytable(comment text, orderVal integer)tableNameRegister 看起来像这样:

 idnum | tablename
-------+------------
     1 | mytable
     2 | othertable

mytable 看起来像这样:

  comment  | orderval
-----------+-------
 comment 1 |     1
 comment 2 |     2

我想要的是从tableNameRegister 中获取tableName 值,然后从该tableName 值中进行选择,但所有这些都在一个查询中。本质上是这样的:

tabName = 'SELECT tableName FROM tableNameRegister WHERE idNum = 1;'
'SELECT * FROM $tabName WHERE orderVal = 2'

理想情况下,这将返回包含comment 2 的行。所以我尝试在子查询中这样做:

'SELECT * FROM (SELECT tableName FROM tableNameRegister WHERE idNum = 1) AS tabname WHERE orderVal = 2;'

但是发现,但这并没有像我想象的那样工作。本质上,它根据子查询的结果返回一种子表,而不是我想要的mytable 的实际值。我想知道是否有一种方法可以在一个查询/使用子查询中完成我的意图?或者这是我必须以编程方式执行并分成两个查询的事情?

【问题讨论】:

【参考方案1】:

这种类型的事情最好通过某种脚本或以其他方式编程来完成。使用 plpgsql 之类的东西我们有更大的灵活性,但即使这样,如果所有表不共享相同的结构或至少不共享相同的列名,那么棘手的事情将是。如果它们确实或可以以某种方式抽象出来,那么以下内容可以帮助您入门:

CREATE OR REPLACE FUNCTION tablequery(id_num int)
RETURNS TABLE (comment varchar, orderval int)
AS $$
DECLARE
tableName varchar(50);
BEGIN
SELECT table_name FROM tableNameRegister WHERE idnum = id_num LIMIT 1 into tableName;
  RETURN QUERY EXECUTE format('SELECT * FROM %I WHERE orderVal = 2;', tableName);
END;
$$ LANGUAGE plpgsql;

select * FROM tableQuery(1);

【讨论】:

以上是关于FROM 子句中的 Postgres 子查询的主要内容,如果未能解决你的问题,请参考以下文章

在子查询的FROM中使用Postgres窗口语句

from 子句中的 JPA/hibernate 子查询

使用 from 子句中的子查询动态选择表名

Psql - from 子句中的子查询 - 不好的做法?

MySQL 子查询 派生表子查询错误

View 的 SELECT 包含 FROM 子句中的子查询