Join的工作流程是怎么样的,怎么进行优化?

1 个回答

  • 无邪
    鸟随鸾凤飞腾远,人伴贤良品自高。
    **join的大概使用是怎么样的?** full outer join 会包含两个表不满足条件的行 left join 会包含左边的表不满足条件的行,一般会使用左边的表作为驱动表。 right join 会包含右边的表不满足条件的行,一般会使用右边的表作为驱动表。 inner join 就是只包含满足条件的行 cross join 从表A循环取出每一条记录去表B匹配,cross join 后面不能跟on,只能跟where **exits 和in,join的区别是什么?** exists是拿外表作为驱动表,外表的数据做循环,每次循环去内表中查询数据,使用适内表比较大的情况 例如 select * from t1 where t1.tid exists (select t2.tid from t2) 转换为伪代码为: ```java //就是t1作为驱动表 List<Row> result = new ArrayList<>(); for(Row r1 in List<Row> t1){ for(Row r2 in List<Row> t2){ if(r1.id = r2.tid){ result.add(r1.join(r2)); } } } ``` 而 in的话正好相反,是那内表作为驱动表,内表的数据做循环,每次循环去外表查询数据,适合内表比较小的情况。 ```java select * from A where cc in (select cc from B) -- 效率低,用到了A表上cc列的索引; select * from A where exists(select cc from B where cc=A.cc) -- 效率高,用到了B表上cc列的索引。 ``` not in 和not exists如果查询语句使用了not in 那么内外表都进行全表扫描,没有用到索引;而not extsts 的子查询依然能用到表上的索引。所以无论那个表大,用not exists都比not in要快。 join的实现其实是先从一个表中找出所有行(或者根据where子句查出符号条件的行),然后去下一个表中循环寻找匹配的行,依次下去,直到找到所有匹配的行,使用join不会去创建临时表,使用in的话会创建临时表,销毁临时表 所以不管是in子查询,exists子查询还是join连接查询,底层的实现原理都是一样的,本质上是没有任何区别的,关键的点在关联表的顺序,如果是join连接查询,MySQL会自动调整表之间的关联顺序,选择最好的一种关联方式。和上面in和exists比较的结论一样,小表驱动大表才是最优的选择方式。
    发布于 2022-02-12 18:55 •IP属地 辽宁
    举报
    评论
    收藏