WHERE慢的下一个和上一个ID

时间:2017-06-29 11:29:18

标签: mysql performance next

我正在尝试解决性能问题。 我有一张名为" pages"其中包含数千页。 有一个名为" status"可以是0,1,2,我想只选择1和2但不是0.只要我添加额外的AND!= 0或IN(1,2)或> = 1,此查询需要0,5秒,没有它安静的快。

以下是我的疑问:

SELECT name, pages.id, urlString, metaTitle, metaDescription, id, 
anchorText
                    FROM pages 
                    INNER JOIN metaDe 
                    ON pages.id=metaDe.pageId 
                    WHERE id = (SELECT min(id) FROM pages WHERE 
linkToPageFunction = ? AND id > ? AND status != 0 )
                    LIMIT 1

                    SELECT name, pages.id, urlString, metaTitle, 
metaDescription, id, anchorText
                    FROM pages 
                    INNER JOIN metaDe 
                    ON pages.id=metaDe.pageId 
                    WHERE id = (SELECT max(id) FROM pages WHERE 
linkToPageFunction = ? AND id < ? AND status != 0 )
                    LIMIT 1

没有&#34; AND状态!= 0&#34;它很快。 我希望它是快速加上如果可能我想使用一个返回两个结果(上一个和下一个)而不是使用两个查询的查询。 有什么建议? 提前致谢

编辑说明:

array (
  0 => 
  array (
    'id' => 1,
    'select_type' => 'PRIMARY',
    'table' => 'metaDe',
    'type' => 'const',
    'possible_keys' => 'PRIMARY,pageId_2,pageId,pageId_3,idxMetaDePageId',
    'key' => 'PRIMARY',
    'key_len' => '4',
    'ref' => 'const',
    'rows' => 1,
    'Extra' => 'Using where',
  ),
  1 => 
  array (
    'id' => 1,
    'select_type' => 'PRIMARY',
    'table' => 'pages',
    'type' => 'const',
    'possible_keys' => 'PRIMARY,id,id_2,id_3',
    'key' => 'PRIMARY',
    'key_len' => '4',
    'ref' => 'const',
    'rows' => 1,
    'Extra' => 'Using where; Using index',
  ),
  2 => 
  array (
    'id' => 2,
    'select_type' => 'SUBQUERY',
    'table' => 'pages',
    'type' => 'ref',
    'possible_keys' => 'PRIMARY,linkToPageFunction,id,status,id_2,id_3,idxPagesForStatusQuery,idxPagesStatus',
    'key' => 'idxPagesForStatusQuery',
    'key_len' => '93',
    'ref' => 'const',
    'rows' => 298725,
    'Extra' => 'Using where; Using index',
  ),
)array (
  0 => 
  array (
    'id' => 1,
    'select_type' => 'PRIMARY',
    'table' => 'pages',
    'type' => 'const',
    'possible_keys' => 'PRIMARY,id,id_2,id_3',
    'key' => 'PRIMARY',
    'key_len' => '4',
    'ref' => 'const',
    'rows' => 1,
    'Extra' => 'Using index',
  ),
  1 => 
  array (
    'id' => 1,
    'select_type' => 'PRIMARY',
    'table' => 'metaDe',
    'type' => 'const',
    'possible_keys' => 'PRIMARY,pageId_2,pageId,pageId_3,idxMetaDePageId',
    'key' => 'PRIMARY',
    'key_len' => '4',
    'ref' => 'const',
    'rows' => 1,
    'Extra' => '',
  ),
  2 => 
  array (
    'id' => 2,
    'select_type' => 'SUBQUERY',
    'table' => 'pages',
    'type' => 'range',
    'possible_keys' => 'PRIMARY,linkToPageFunction,id,status,id_2,id_3,idxPagesForStatusQuery,idxPagesStatus',
    'key' => 'idxPagesForStatusQuery',
    'key_len' => '97',
    'ref' => NULL,
    'rows' => 5,
    'Extra' => 'Using where; Using index',
  ),
)

由于无论出于何种原因我无法回答这个帖子,我在这里给出了答案和解决方案。

谢谢大家。有时你需要事情并谈论解决它。我想我刚刚找到了(简单)解决方案。

这就是我现在正在做的事情。我不知道为什么我之前没有这样。

下一步

            SELECT name, pages.id, urlString, metaTitle, metaDescription, id, anchorText
            FROM pages 
            INNER JOIN metaDe 
            ON pages.id=metaDe.pageId 
            WHERE id > ? AND status IN (1, 2) AND linkToPageFunction = ?
            ORDER BY id ASC  LIMIT 1

            SELECT name, pages.id, urlString, metaTitle, metaDescription, id, anchorText
            FROM pages 
            INNER JOIN metaDe 
            ON pages.id=metaDe.pageId 
            WHERE id < ? AND status IN (1, 2) AND linkToPageFunction = ?
            ORDER BY id DESC  LIMIT 1

1 个答案:

答案 0 :(得分:0)

您的pages表格上似乎没有包含status字段的索引。添加这样的索引,您的查询速度应该会提高很多。

create index idxPagesStatus on pages (status);

甚至

create index idxPagesForStatusQuery on pages (linkToPageFunction, id, status);

包含查询中的所有字段。此外,在您的metaDe tabke页面上,我也可以使用索引。

create index idxMetaDePageId on metaDe (pageId);

另外,如果你知道pages.id键肯定是顺序的(即,如:1,2,3,4,5 ......),并且没有删除,你可以简单地做:

SELECT
  name,
  pages.id,
  urlString,
  metaTitle,
  metaDescription,
  id, 
  anchorText
FROM
  pages 
left JOIN
  metaDe ON pages.id=metaDe.pageId 
WHERE 
  abs(2-id)=1;