在 MYSQL 的子查询中使用 LIMIT 关键字的替代方法

Posted

技术标签:

【中文标题】在 MYSQL 的子查询中使用 LIMIT 关键字的替代方法【英文标题】:Alternative to using LIMIT keyword in a SubQuery in MYSQL 【发布时间】:2012-10-10 00:34:51 【问题描述】:

我有一个包含以下列的表 TEST:

code_ver (VARCHAR)
suite (VARCHAR)
date (DATE)

现在我想选择不同值为 code_ver & code_ver NOT LIKE '%DevBld%' sorted by date desc. 的 10 行

所以我写了以下查询:

select * 
  from test 
 where code_ver IN (select DISTINCT code_ver 
                      from test 
                     where code_ver NOT LIKE '%DevBld%' 
                     ORDER by date DESC LIMIT 10);

这个查询应该可以正常工作,但我的 mysql 版本说:

这个版本的 MySQL 还不支持 'LIMIT & IN/ALL/ANY/SOME 子查询'

有人可以建议我替代此查询吗?

【问题讨论】:

向我们展示示例数据和您想要的结果。 【参考方案1】:

Layke 建议的答案在我的权限范围内是错误的。在子查询中使用限制的意图是使主查询在从子查询中获取的有限记录上运行。如果我们将限制保持在外部,那么限制对子查询毫无用处。

由于mysql还不支持子查询的限制,所以可以使用JOIN,如下:

       
    SELECT * FROM test
    JOIN 
    (
        SELECT DISTINCT code_ver 
        FROM test 
        WHERE code_ver NOT LIKE '%DevBld%' 
        ORDER BY date DESC LIMIT 10
    ) d
    ON test.code_ver
    IN (d.code_ver)
    ORDER BY xyz;

【讨论】:

为什么“(select DISTINCT code_ver from test where code_ver NOT LIKE %DevBld%' ORDER by date DESC LIMIT 10)”不被认为是子查询并且允许在其中使用 LIMIT? 如果我们将查询作为其他查询的派生数据源,例如提问者已放入“select * from test where code_ver IN (select DISTINCT code_ver from test where code_ver NOT LIKE '%DevBld%' ORDER by date DESC LIMIT 10); " 然后我们将其称为子查询,但根据 mysql 当前规则 LIMIT 在子查询中是不允许的,这就是为什么我建议使用 JOIN 来达到此目的。【参考方案2】:

您也可以使用相同的查询,只需在子查询之前添加一层额外的选择。就是这样。它会起作用的。

select * from test 
where code_ver IN (select * from (select DISTINCT code_ver 
                      from test 
                     where code_ver NOT LIKE '%DevBld%' 
                     ORDER by date DESC LIMIT 10) as t1);

【讨论】:

谢谢,这个解决方案有效,值得接受 如此简单,完美运行。 应该是公认的答案。【参考方案3】:

将子查询放入派生表中:

   SELECT test.*
     FROM test
LEFT JOIN (SELECT DISTINCT code_ver
             FROM mastertest
            WHERE code_ver NOT LIKE '%DevBld%'
            ORDER BY `date` DESC
            LIMIT 10) d
    USING (code_ver)
    WHERE d.code_ver IS NOT NULL;

(当然,您也可以 RIGHT JOIN 并删除外部 WHERE 条件。)

【讨论】:

我试过这个。它仍然像 84 行一样返回我,而且它们也不是唯一的....:( @sagarvikani,那我不明白你想做什么。假设您执行了CREATE TABLE t SELECT DISTINCT code_ver ... LIMIT 10,然后使用WHERE code_ver IN (SELECT code_ver FROM t) 尝试了您的原始查询。我希望你仍然会得到 84 行。 我刚刚执行了你上面写的查询【参考方案4】:

您得到的错误不完全是因为 MySQL 的版本。我认为所有版本都支持这一点。您必须更改 LIMIT 10 位置并将其放在“)”之后。请让我知道这对你有没有用。我在我的身上运行了下面的那个,它可以工作。

例如

SELECT * FROM test where name IN (
           SELECT DISTINCT name 
           FROM projects 
           WHERE name NOT LIKE "%DevBld%"  
           ORDER by date_created DESC
 ) LIMIT 10;

更新:试试下面的,这样顺序就可以了:

 SELECT * FROM  automation.e2e_projects WHERE name IN (
       SELECT DISTINCT name 
       FROM automation.e2e_projects
       WHERE name NOT LIKE "%DevBld%"
 ) ORDER by date_created DESC LIMIT 10;

【讨论】:

从 SELECT * 开始。第一行! 如果有多行与名称相关联,则它不起作用,它只会显示 test 表的 10 行。我认为这不是问题的正确解决方案。 派生表答案似乎更正确。

以上是关于在 MYSQL 的子查询中使用 LIMIT 关键字的替代方法的主要内容,如果未能解决你的问题,请参考以下文章

MySQL基础语法之子链接查询和特殊查询(union 和 limit)

SQL-子查询;union;limit

mysql 子查询中 使用 limit

MySQL单表的CRUD及多表查询

MYSQL基础九--子查询和连接

MySQL 简单查询