You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MySQL十万级blog表各子分类取Top6记录的性能与结果咨询

MySQL分组取前N条记录:正确性与性能优化

先直接回答你的两个问题,再展开细节:

1. 该查询能否生成预期结果?

基本可以,但有个容易踩的小坑。你的思路是对的:通过变量@rn和@prev给每个sub_cat_id分组编号,外层筛选出编号≤6的记录,确实能拿到每个目标分类下按created_date倒序的前6条。

但要注意:MySQL中如果不显式初始化用户变量,第一次运行时可能因为变量残留值导致编号错误(比如之前有其他查询用过@rn或@prev,初始值不是1或NULL)。建议修改成带变量初始化的版本,确保结果完全符合预期:

SELECT * FROM (
    SELECT 
        sub_cat_id, 
        title, 
        created_date,
        @rn:=IF(@prev = sub_cat_id, @rn + 1, 1) AS rn, 
        @prev:=sub_cat_id AS previd
    FROM 
        blog,
        (SELECT @rn:=1, @prev:=NULL) AS init -- 显式初始化变量
    WHERE 
        type = 'BLOG' 
        AND FIND_IN_SET(sub_cat_id, '1,2,8') 
        AND created_date <= NOW() 
    ORDER BY 
        sub_cat_id DESC, 
        created_date DESC
) AS records 
WHERE rn <= 6

2. 这是否是最优且最快的方式?

不是,尤其是在10万条记录的表中,性能可能存在瓶颈。

你的原查询需要先筛选出所有符合条件的记录,再做全局排序,最后逐一编号。如果这三个分类下的总记录数很多(比如每个分类有几万条),全局排序的开销会很大,大概率触发filesort,拖慢查询速度。

更优的替代方案:用UNION ALL拆分查询

针对固定的分类(1、2、8),直接对每个分类单独查询前6条,再用UNION ALL合并结果,性能会好很多:

(SELECT sub_cat_id, title, created_date 
 FROM blog 
 WHERE type='BLOG' AND sub_cat_id=1 AND created_date<=NOW() 
 ORDER BY created_date DESC LIMIT 6)
UNION ALL
(SELECT sub_cat_id, title, created_date 
 FROM blog 
 WHERE type='BLOG' AND sub_cat_id=2 AND created_date<=NOW() 
 ORDER BY created_date DESC LIMIT 6)
UNION ALL
(SELECT sub_cat_id, title, created_date 
 FROM blog 
 WHERE type='BLOG' AND sub_cat_id=8 AND created_date<=NOW() 
 ORDER BY created_date DESC LIMIT 6)

这个方案的优势:

  • 每个子查询精准定位单个分类,配合索引可以直接快速获取前6条,不需要处理大量冗余数据
  • 避免了全局排序和变量编号的额外开销,执行效率更高

索引优化(两种方案都适用)

不管用哪种查询方式,都建议创建一个联合索引来最大化性能:

CREATE INDEX idx_blog_type_subcat_created ON blog (type, sub_cat_id, created_date DESC);

这个索引可以直接覆盖WHERE条件筛选和ORDER BY排序需求,让查询完全走索引,避免全表扫描或filesort,大幅提升速度。

方案选择总结

  • 原方案更适合分类不固定(比如需要动态传入多个分类ID)的场景,但一定要做好变量初始化和索引优化
  • UNION ALL方案在分类固定时性能最优,代码也更直观、易维护

内容的提问来源于stack exchange,提问作者Mike

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 08:17:23