【问题标题】:Select rows based on long list of two columns根据两列的长列表选择行
【发布时间】:2020-09-04 20:54:42
【问题描述】:

假设我有下表

CREATE TABLE IF NOT EXISTS "PROPS" (
   "O_TYPE_ID"  UUID NOT NULL,
   "O_ID"       UUID NOT NULL,
   "R_TYPE_ID"  UUID NOT NULL,
   "NAME"       VARCHAR NOT NULL,
   "VALUE"      VARCHAR,

   CONSTRAINT PK_PROPS  PRIMARY KEY ("O_ID", "R_TYPE_ID", "NAME")
    );

现在我有一个列表列表,这是我想用来查询 Postgres 的列表。意思是我有一个

的列表
List((O_ID.type, NAME.type))

我想列出所有具有这两种类型组合的记录,我可以使用 IN 运算符的单个列表,在上述情况下如何查询 list os 列表值?一个天真的实现是用两个相等子句和 and 运算符执行 where,但在我的情况下,如果列表太大意味着 IO 太多,您将如何处理以非常简单的方式处理列表列表的场景没有太多IO的优化方式。使用 9.4+ Postgres。

【问题讨论】:

    标签: postgresql postgresql-9.4


    【解决方案1】:

    许多可能的方式之一:传递两个数组,一个数组O_ID(我们将其命名为o_id_arr),一个数组NAME(我们将其命名为name_arr);然后并行取消嵌套并加入:

    SELECT p.*
    FROM   (o_id_arr, name_arr) AS t("O_ID", "NAME")
    JOIN   "PROPS" p USING ("O_ID", "NAME");
    

    Postgres 9.4 引入了并行取消嵌套多个数组的功能,因此应该适合您:

    或者,特别是对于大表和非常长的列表,创建一个临时表,将您的数据插入其中,可选地ANALYZE 它,然后加入它:

    CREATE TEMP TABLE tmp ("O_ID" UUID, "NAME" VARCHAR);
    
    INSERT INTO tmp VALUES (..., ...), (..., ...);
    
    ANALYZE tmp;
    
    SELECT p.*
    FROM   tmp
    JOIN   "PROPS" p USING ("O_ID", "NAME")
    

    通常,您应该在"PROPS" ("O_ID", "NAME") 上有一个多列索引以提高性能。但是看到"O_ID"uuid 类型,("O_ID", "R_TYPE_ID", "NAME") 上的奇数 PK 索引可能会起作用。为什么是“奇怪”?两个 UUID 和一个 varchar 列对于一个好的 PK 来说似乎过于臃肿......

    相关:

    除此之外:摆脱那些乏味且容易出错的双引号标识符。使用不带双引号的合法小写标识符。见:

    未加引号的约束名称 PK_PROPS 保存为 pk_props ...

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-01-01
      • 1970-01-01
      • 2018-03-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-10-11
      • 2014-06-15
      相关资源
      最近更新 更多