SQL查询-尽量避免结果集中的重复数据



这是我想了很久的问题。我试着用一个例子来解释,但这是一个一般性的问题。

假设你有两张桌子:

  1. users,其中包含名字、姓氏。。。的
  2. posts,保存用户撰写的帖子,包含标题、文本等字段

现在,假设我想显示在过去24小时内创建的所有帖子。在这个表中,我想显示名字、姓氏。。。创建此帖子的用户的。查询可能看起来像:

选择。。。FROM posts,users WHERE posts.user_id=users.id AND[过去24小时]

现在,谈谈我的问题。由于很可能一个用户在过去24小时内创建了多个帖子,我们基本上是在检索他/她的名字、姓氏。。。一次又一次换句话说,上面查询的结果集包含重复的数据(但不包含重复的行)。

不是更好吗

  1. 选择。。。FROM张贴地点[过去24小时]
  2. 选择。。。FROM用户id IN(SELECT DISTINCT user_id FROM posts where[last 24 hours])
  3. 在应用程序级别或sql过程中,将第一个查询的结果与第二个查询的查询结果进行映射,以找出名字、姓氏。。。如果标识符(主键)是某种哈希图、数组或类似的索引/键,那么这可以很容易地完成

我知道这是一个非常普遍的问题,但任何见解都是受欢迎的。谢谢

任何一种方法都应该有效,但您找到了重要的部分:

在应用程序级别执行

对我来说,我会提取重复的数据,这样我的结果集的每一行都包含了我需要的所有数据。SQL在JOIN和集合操作方面比几乎任何声明性语言都更有效率。

如果你把数据放在一起,如果需要的话,你会更容易把它分解到下游,而且你只需要对数据库进行一次调用,而不是两次。

这样做的好处随着重复数据的增长而减少。如果只是几个领域,影响不大。如果是几十个冗余数据字段,那么性能差异将更加明显。

对于您的特定示例,最好在一个查询中完成所有操作

如果让您感到困扰,您可以在应用程序级别消除重复,但与多次调用数据库相比,为同一用户多次返回的2或3个额外字段并不是很重要。

最佳解决方案取决于每个表中的行数以及每个用户每天的帖子数。

如果有相对较少的帖子和大量的用户,那么一次性选择帖子和用户是可以的

如果用户很少,每个用户有很多帖子,最好使用第二个选项,分别选择它们。首先,你会选择过去24小时内的帖子,然后你会选择这样的作者:

SELECT users.id, first_name, last_name
FROM users
LEFT JOIN posts ON users.id = user_id
WHERE [posts in the last 24 h]

我认为最好的解决方案是选择用户,whitch的消息持续24小时,然后根据用户id选择消息。

1. step:
SELECT DISTINCT id, first_name, last_name
FROM users INNER JOIN
posts ON posts.user_id = users.id
WHERE [last 24 hours]
2. step:
SELECT *
FROM posts
WHERE user_id = @userId AND [last 24 hours]

这种方式会导致更多的数据库调用,但内存使用率较低,因为一次只为一个用户检索消息。

最新更新