mysql 联接查询算法之Block Nested-Loop Join(BNL) 二

说白了,扫描一个表的过程复杂在它需要频繁地在内存和磁盘之间移动数据。
先说最重要的,这个过程涉及到将表从磁盘加载到内存,然后进行匹配,但内存可能不够大,需要释放之前的记录。
去年我们跑的那个项目,大概3 000量级的数据,就经常遇到内存不足的问题。

另外一点,SNLJ算法在两表联接时,被驱动表需要被多次访问,这直接影响了性能。
我一开始也以为SNLJ是最优的,后来发现不对,它其实是效率最低的,因为它每次都要从磁盘读取数据。

还有个细节挺关键的,MySQL在执行Join操作时,会尝试使用IndexNested-LoopJoin算法,但如果Join的列没有索引,就会退回到SNLJ算法。
这个点很多人没注意,其实SNLJ算法的性能非常差,因为它会产生大量的I/O操作。

最后提醒一下,使用BlockNested-LoopJoin算法时,可能会多次扫描被驱动表,占用磁盘IO资源,同时也会占用大量的CPU资源。
如果你发现系统性能下降,可以尝试增大join_buffer_size的值,减少对被驱动表的扫描次数。
我觉得值得试试,看看是否能够提升性能。

哎呦,这代码一看就是百度知道的页面,密密麻麻的都是技术细节。
说实话,我这种混迹问答论坛行业的老兵,对这些东西也不太懂,但多少能看出点门道。

你看,这里有个“帮助”和“意见反馈”,还有“投诉举报”,这些都是为了规范用户行为,保护大家权益的。
京ICP证03 01 7 3 号-1 ,这应该是百度知道的官方网站备案号,表明它是一个正规网站。

然后,这段代码里有很多“[xss_clean]”,这都是JavaScript代码,用来实现页面的各种功能。
比如,这个“[xss_clean]”,这是用来防止跨站脚本攻击的,挺重要的。

还有这个“window.tt=1 7 7 3 8 8 1 4 1 7 ;”,看起来像是某个变量赋值,但具体作用我不太清楚。

再往下看,这里有一大堆资源映射,像是“common-new:widget/lib/jquery/jquery.origin.js”、“common-new:widget/js/ui/address/sitedata_bas.js”等等,这些都是页面上用到的各种资源文件。

还有这个“common-new:widget/userbar-renew/userbar-renew.js”,这是用户栏的更新脚本,应该是用来美化用户界面或者增加新功能的。

最后,这里还有一些监测和日志记录的代码,比如“log.send(params);”,这应该是用来记录用户行为的,方便网站运营者分析数据。

总之,这个页面代码挺复杂的,涉及到很多前端技术。
我当时也没想明白,不过至少能看出它是一个功能齐全、安全性较高的问答平台。

联合索引查询原理及生效规则

哎哟,联合索引这玩意儿啊,得好好说说。
咱们先来聊聊查询原理。

想象一下,B+树结构就像一棵大树,联合索引就是树的枝桠。
这棵树里,数据页按照索引字段的顺序排好队,先看第一个字段,如果一样再看第二个,就这么排下去。
数据页之间还用双向链表连着,方便找。

那查询呢?就像找东西,先在索引页上二分查找,找到对应的数据页。
然后,在数据页里再二分查找,看班级、姓名和科目,最后找到记录。
找到主键ID后,就能通过聚簇索引拿到完整记录了。

再说说生效规则吧。

首先是等值匹配规则,就是查询条件里的字段名和顺序得跟索引一样,还得用等号。
即便字段顺序不一样,MySQL也会帮你调整,让它匹配索引结构。

然后是“最左侧列匹配”,就像树干一样重要。
比如索引是(class_name,student_name,subject_name),你可以用class_name或class_name和student_name来查,但要是直接查subject_name,那索引就不管用了。

“最左前缀匹配原则”呢,就是用LIKE查询时,得从确定字符开始,比如'1 %',这样能用索引。
要是开头就是通配符,比如'%班',那索引就不管用了。

范围查找规则也很关键,比如查class_name的范围,可以用索引。
但要是查非最左侧列的范围,那就不行。

还有“等值匹配+范围匹配的规则”,先等值匹配,再范围查询,这样等值匹配可以用索引,但范围查询得是下一列才行。

总结一下,联合索引能提高查询效率,但得看查询条件是否符合索引结构。
设计联合索引时,得考虑查询场景,合理安排字段顺序,写SQL语句也得符合索引使用规则。
这就像给电脑装了加速器,得会用才能发挥最大效果。