实际限制“where in”子句

时间:2011-07-07 09:15:03

标签: mysql where-clause

我有一个相当简单的表,大约有一百万行。

id  |  my_col  |  other1  |  other 2 | ...

此表中有大约15k个不同的my_col值,而my_col上有一个索引。我有一组7k my_col值,我需要从这个表中删除。

在SQL中做什么更有效(我目前正在使用MySQL,但将来可能会移植到MS SQL。)

是否a)在我的java应用程序代码中,遍历所有my_col值并在每个值上调用sql delete。

for (String my_colValue : listMyCol) {
   [delete from my_table where my_col = my_colValue]
}

或b)使用“where in”子句构建包含所有这些值的单个SQL [large]语句?

delete from my_table where my_col in ('aaa', 'aab', 'aac', ...)

我猜它是b),但我不确定在“where in”子句中指定约7k值是否效率低。

为了它的价值,我的应用服务器和数据库服务器都托管在亚马逊,但在不同的层上。

3 个答案:

答案 0 :(得分:2)

c)重新创建你的桌子。

你要删除一半的行,所以想一想。 虽然a)和b)可能会永远占用,但重新制作你的桌子会很诡异但是很快。

您需要在临时表中加载7k值,然后很容易:

CREATE TABLE newMyTable
AS
SELECT myTable.*
FROM myTable
    INNER JOIN myValues
        ON myTable.my_col = myValues.my_col

或者,如果你不能创建表,也许这会足够快:

DELETE FROM myTable t
WHERE EXISTS
(
    SELECT *
    FROM myValues v
    WHERE t.my_col = v.my_col
)

但是你需要记住的唯一事情是:你必须用你的7k值创建一个表。

答案 1 :(得分:2)

使用WHERE IN的实际限制是你可以在多大程度上进行SQL查询。这是由MySQL的max_packet_size配置变量定义的。其他任何事情只是性能权衡。为了找出最快的方法,基准测试仍然效果最好。

答案 2 :(得分:1)

我会选择第一个选项,但我会将所有内容都放在交易中。这样,提交将在最后,而不是在每个DELETE语句之后。

搜索许多记录时,索引效率低下。