【问题标题】:joining latest of various usermetadata tags to user rows将最新的各种用户元数据标签加入用户行
【发布时间】:2008-08-24 17:48:12
【问题描述】:

我有一个带有用户表(用户 ID、名字、姓氏)和用户元数据表(用户 ID、代码、内容、创建日期时间)的 postgres 数据库。我通过代码将有关每个用户的各种信息存储在 usermetadata 表中,并保留完整的历史记录。例如,一个用户(用户 ID 15)有以下元数据:

15, 'QHS', '20', '2008-08-24 13:36:33.465567-04'  
15, 'QHE', '8', '2008-08-24 12:07:08.660519-04'  
15, 'QHS', '21', '2008-08-24 09:44:44.39354-04'  
15, 'QHE', '10', '2008-08-24 08:47:57.672058-04'  

我需要获取所有用户的列表以及每个用户元数据代码的最新值。我以编程方式完成了这项工作,当然速度非常慢。在 SQL 中我能想到的最好方法是加入子选择,这也很慢,我必须为每个代码做一个。

【问题讨论】:

    标签: database postgresql


    【解决方案1】:

    这实际上在 PostgreSQL 中并不难做到,因为它的 SELECT 语法中有 "DISTINCT ON" 子句(DISTINCT ON 不是标准 SQL)。

    SELECT DISTINCT ON (code) code, content, createtime
    FROM metatable
    WHERE userid = 15
    ORDER BY code, createtime DESC;
    

    这会将返回的结果限制为每个唯一代码的第一个结果,如果您按创建时间降序对结果进行排序,您将获得每个结果中的最新结果。

    【讨论】:

      【解决方案2】:

      我想你不愿意修改你的架构,所以恐怕我的回答可能没有多大帮助,但是这里是......

      当您插入“弃用日期”时,一种可能的解决方案是将时间字段留空,直到它被更新的值替换。另一种方法是使用“活动”列扩展表,但这会引入一些冗余。

      经典的解决方案是同时设置“Valid-From”和“Valid-To”字段,其中“Valid-To”字段为空白,直到其他条目变为有效。这可以通过使用触发器或类似方法轻松处理。使用约束来确保每种类型只有一个有效项将确保数据完整性。

      这些的共同点是有一种确定当前字段集的方法。您只需选择具有活动用户和 NULL 'Valid-To' 或 'deprecation date' 或真正的 'active' 的所有条目。

      您可能有兴趣查看temporal databases 上的维基百科条目和文章​​A consensus glossary of temporal database concepts

      【讨论】:

        【解决方案3】:

        子选择是做这种事情的标准方法。您只需要对 UserId、Code 和 Date 设置唯一约束 - 然后您可以运行以下命令:

        SELECT * 
        FROM Table
        JOIN (
           SELECT UserId, Code, MAX(Date) as LastDate
           FROM Table
           GROUP BY UserId, Code
        ) as Latest ON
           Table.UserId = Latest.UserId
           AND Table.Code = Latest.Code
           AND Table.Date = Latest.Date
        WHERE
           UserId = @userId
        

        【讨论】:

          猜你喜欢
          • 2017-07-17
          • 1970-01-01
          • 2020-02-01
          • 2016-12-01
          • 2017-03-09
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多