【问题标题】:UNION vs multiple SELECT for getting previous and next rowUNION vs 多个 SELECT 用于获取上一行和下一行
【发布时间】:2013-09-05 15:04:24
【问题描述】:

这可能是mysql union vs multiple queries 的重复问题,除了问题过于笼统,而且此问题针对特定情况。

首先,我认为有两个选项,哪个更好 表现明智。第一个是使用单独的查询获取上一行和下一行。以下为伪代码:

sql->query("SELECT * FROM tbldata WHERE id < 3 ORDER BY id DESC LIMIT 1");
$prev = sql->getRecord();
sql->query("SELECT * FROM tbldata WHERE id > 3 ORDER BY id LIMIT 1");
$next = sql->getRecord();

另一种解决方案是仅对 UNION 使用一个查询。

sql->query("(SELECT * FROM tbldata WHERE id > 3 ORDER BY id DESC LIMIT 1) UNION
            (SELECT * FROM tbldata WHERE id < 3 ORDER BY id LIMIT 1)");
$row = sql->getRecords();
if (count($row) > 1) {
   $prev = $row[0];
   $next = $row[1];
} elseif (count($row) == 0) {
} elseif ($row[0]->id > 3) {
   $next = $row[0];
} else {
   $prev = $row[0];
}

哪一个是此类问题的最佳实践?

【问题讨论】:

标签: php mysql


【解决方案1】:

如果我不得不猜测,UNION 总体上可能更快,只是因为它减少了对数据库的请求数量,但我强调,这是一个猜测,它取决于许多因素,唯一的知道方法是分析代码并检查。

实际上,它可能几乎没有什么区别。除非有异常情况,例如与数据库服务器的连接速度非常慢。

我的建议是,使用使代码更整洁和更易于阅读的任何一种,直到有理由更改它 - 即。直到您的系统分析表明这是系统中的瓶颈。

【讨论】:

    【解决方案2】:

    根据我的经验,我认为UNION 比其他人更快。

    也试试这个。

    SELECT * , IF( id >3, 1, 0 ) AS NextFlag, IF( id <3, 1, 0 ) AS PrevFlag FROM tbldata
    WHERE id <= 3+1
    HAVING NextFlag =1
    OR PrevFlag =1
    ORDER BY id DESC
    LIMIT 2 
    

    【讨论】:

      【解决方案3】:
      $sql->query('SELECT t.*
                   FROM table t
                   WHERE t.id IN ('.($id-1).', '.($id+1).')');
      $rows = sql->getRecords();
      
      $next = $prev = false;
      
      if (is_array($rows) && $rows) {
          $next = $rows[0];
      
          if (isset($rows[1])) {
              $prev = $rows[1];         
          } elseif ($rows[0]->id < $id) {
              $prev = $next;
              $next = false;
          }
      }
      

      一个带有 PRIMARY 索引的请求(如果 id 是您的 PRIMARY KEY)。优于 UNION 或 2 个请求。

      【讨论】:

      • 主键总是顺序的,不是吗?当然,您可以随时添加 ORDER BY t.id ASC。
      • 如果一行已被删除,则不会。
      • ...如果您没有在“id”字段上使用自动增量。
      猜你喜欢
      • 2020-12-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-01-14
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多