sql - 使用内连接删除需要 40 多秒才能删除 500 行
问题描述
我有这个要求:
delete L
from L
inner join M on L.id = M.ref_id
or L.id = M.news_id
完成删除 588 行需要 39 到 50 秒。
如果在我的查询中替换delete L from L
为,则选择非常快 0,015 秒select * from L
希望你能帮助我在这里缺少什么,这里有什么问题?
解决方案
从大型聚簇表中删除行通常很慢。
评论中讨论的著名“BETWEEN”是聚集索引的一个分区,它从您的连接中获取最小值和最大值。所以建议批量删除。
我想可能没有什么一般性建议,但它总是取决于不同的因素,例如数据量、硬件、内存、日志文件大小等。 - 批量删除行。最佳批量大小取决于环境,但通常在 10K 到 100K 左右。- 按聚集索引的顺序删除 - 如果可能,将您的恢复模式设置为 BULK/SIMPLE 以减少日志记录。- 如果可能的话,从子表中删除约束,如外键约束。- 如果可能,禁用非聚集索引 - 根据您要删除的数据量,最好将数据导出到新表,然后删除旧表或为将来保留不同的名称参考。如您所见,主要取决于情况和环境。
这是最好的答案,“也许你需要调整系统,而不是查询”
但是从删除语句中,我更愿意看到大部分成本来自删除本身。了解,聚集索引是将数据存储在具有聚集索引的表中的位置。删除时,您将从集群中删除。这并不是说您可能无法进一步调整它,但您会看到非常正常,甚至是理想的行为。如果没有确切地看到你在做什么,很难提出建议,但可能是你做得很好。在这种情况下,也许您需要调整系统,而不是查询。获得更快的磁盘。确保您没有承受内存压力。检查您的等待统计信息,以了解大部分工作在服务器上完成的位置,并从那里进行调整。
如果你不能做任何这些事情,使用循环逐行删除可能会更快......
推荐阅读
- javascript - 有没有办法在 JavaScript 中删除记录,同时保持其顺序和数字序列
- hex - 有人可以帮我用十六进制做无符号减法吗
- c# - 使用从文件 C# 中读取的存储数组值
- batch-file - 如何制作打开任务管理器的批处理文件?
- javascript - 在动态选择上运行 Pretty Dropdown
- node.js - json的react处理
- java - Android:com.google.firebase.database.DatabaseException:无法将 java.lang.String 类型的对象转换为 VirtualMoney 类型
- java - 需要帮助找出我的代码中的错误
- mysql - PutElasticsearchHttpRecord:封装的令牌和分隔符之间的字符无效
- jquery - 样式化复选框并按标签显示内容不起作用