原标题:MySQL Join竟然可以这么玩?根据条件进行复制

本文节选自松华老师的《SQL优化专栏》

郑松华,知数堂SQL 优化班老师

现任 CCmediaService DBA,主要负责数据库优化相关工作

擅长SQL优化 ,数据核对

大家好,我是知数堂SQL优化班老师,网名:骑龟的兔子

今天给大家带来根据条件进行复制的案例

背景说明:

如下,有一个表t1 ,有三行数据

with t1 as (

select 1 seq ,'AK' id ,'A' type ,'g1' goods from dual union all

select 2 seq ,'PS' id ,'B' type ,'iphone' goods from dual union all

select 3 seq ,'BE' id ,'B' type ,'g2' goods from dual

)

select * from t1 ;

+-----+----+------+--------+

| seq | id | type | goods |

+-----+----+------+--------+

| 1 | AK | A | g1 |

| 2 | PS | B | iphone |

| 3 | BE | B | g2 |

+-----+----+------+--------+

3 rows in set (0.00 sec)

现在需求是,根据type 的值'A','B' 要求,如果是'A' 那么还是原来的行数

如果是'B' 那么需要复制五行数据。

如下所示

no | seq | id | type | goods

1, 1, AK, A, g1

2, 2, PS, B, iphone

3, 2, PS, B, t2

4, 2, PS, B, t3

5, 2, PS, B, t4

6, 2, PS, B, t5

7, 3, BE, B, g2

8, 3, BE, B, t2

9, 3, BE, B, t3

10, 3, BE, B, t4

11, 3, BE, B, t5

思路:

我们先来对这个需求进行分析,

第一、因为对行进行复制,所以需要一个复制表

第二、根据条件进行复制

第三、对每个条件的第一个值用t1表的goods进行替换

优化过程:

根据如上所示,

第一、因为对行进行复制,所以需要一个复制表:

先创建一个复制表,这里所涉及两种情况,因为最多复制5行,A种类型可以看做是id为1

with t2 as (

select 1 id ,'t1' a1 from dual union all

select 2 id ,'t2' a1 from dual union all

select 3 id ,'t3' a1 from dual union all

select 4 id ,'t4' a1 from dual union all

select 5 id ,'t5' a1 from dual

)

select * from t2

+----+----+

| id | a1 |

+----+----+

| 1 | t1 |

| 2 | t2 |

| 3 | t3 |

| 4 | t4 |

| 5 | t5 |

+----+----+

第二、根据条件进行复制:

我们这里设置了一个连接条件 ,就是当type='A'的时候我们返回1

当type='B'的时候 我们返回5

然后我们进行了一个>= join

with t1 as (

select 1 seq ,'AK' id ,'A' type ,'g1' goods from dual union all

select 2 seq ,'PS' id ,'B' type ,'iphone' goods from dual union all

select 3 seq ,'BE' id ,'B' type ,'g2' goods from dual

),

t2 as (

select 1 id ,'t1' a1 from dual union all

select 2 id ,'t2' a1 from dual union all

select 3 id ,'t3' a1 from dual union all

select 4 id ,'t4' a1 from dual union all

select 5 id ,'t5' a1 from dual

)

select * from t1 join t2

on case when t1.type = 'A' then 1

when t1.type = 'B' then 5 end >= t2.id

order by seq ,t1.id

+-----+----+------+--------+----+----+

| seq | id | type | goods | id | a1 |

+-----+----+------+--------+----+----+

| 1 | AK | A | g1 | 1 | t1 |

| 2 | PS | B | iphone | 1 | t1 |

| 2 | PS | B | iphone | 2 | t2 |

| 2 | PS | B | iphone | 3 | t3 |

| 2 | PS | B | iphone | 4 | t4 |

| 2 | PS | B | iphone | 5 | t5 |

| 3 | BE | B | g2 | 1 | t1 |

| 3 | BE | B | g2 | 2 | t2 |

| 3 | BE | B | g2 | 3 | t3 |

| 3 | BE | B | g2 | 4 | t4 |

| 3 | BE | B | g2 | 5 | t5 |

+-----+----+------+--------+----+----+

如上所示,我们就完成了 有条件的复制

剩下就剩最后一步

第三、对每个条件的第一个值用t1表的goods进行替换:

我们可以利用case when 语句对t2.id =1的时候用t1.goods其余的用t2.a1进行替换

with t1 as (

select 1 seq ,'AK' id ,'A' type ,'g1' goods from dual union all

select 2 seq ,'PS' id ,'B' type ,'iphone' goods from dual union all

select 3 seq ,'BE' id ,'B' type ,'g2' goods from dual

),

t2 as (

select 1 id ,'t1' a1 from dual union all

select 2 id ,'t2' a1 from dual union all

select 3 id ,'t3' a1 from dual union all

select 4 id ,'t4' a1 from dual union all

select 5 id ,'t5' a1 from dual

)

select

t1.seq,t1.id,t1.type,

case when t2.id =1 then t1.goods

else t2.a1 end goods

from t1 join t2

on case when t1.type = 'A' then 1

when t1.type = 'B' then 5 end >= t2.id

order by seq ,t1.id

+-----+----+------+--------+

| seq | id | type | goods |

+-----+----+------+--------+

| 1 | AK | A | g1 |

| 2 | PS | B | iphone |

| 2 | PS | B | t2 |

| 2 | PS | B | t3 |

| 2 | PS | B | t4 |

| 2 | PS | B | t5 |

| 3 | BE | B | g2 |

| 3 | BE | B | t2 |

| 3 | BE | B | t3 |

| 3 | BE | B | t4 |

| 3 | BE | B | t5 |

+-----+----+------+--------+

最后一步就是赋予序列号,MySQL 8.0 有窗口函数

with t1 as (

select 1 seq ,'AK' id ,'A' type ,'g1' goods from dual union all

select 2 seq ,'PS' id ,'B' type ,'iphone' goods from dual union all

select 3 seq ,'BE' id ,'B' type ,'g2' goods from dual

),

t2 as (

select 1 id ,'t1' a1 from dual union all

select 2 id ,'t2' a1 from dual union all

select 3 id ,'t3' a1 from dual union all

select 4 id ,'t4' a1 from dual union all

select 5 id ,'t5' a1 from dual

)

select

row_number over( order by t1.seq ,t1.id) no,

t1.seq,t1.id,t1.type,

case when t2.id =1 then t1.goods

else t2.a1 end goods

from t1 join t2

on case when t1.type = 'A' then 1

when t1.type = 'B' then 5 end >= t2.id

+----+-----+----+------+--------+

| no | seq | id | type | goods |

+----+-----+----+------+--------+

| 1 | 1 | AK | A | g1 |

| 2 | 2 | PS | B | iphone |

| 3 | 2 | PS | B | t2 |

| 4 | 2 | PS | B | t3 |

| 5 | 2 | PS | B | t4 |

| 6 | 2 | PS | B | t5 |

| 7 | 3 | BE | B | g2 |

| 8 | 3 | BE | B | t2 |

| 9 | 3 | BE | B | t3 |

| 10 | 3 | BE | B | t4 |

| 11 | 3 | BE | B | t5 |

+----+-----+----+------+--------+

谢谢大家~ 欢迎转发

如有关于SQL优化方面疑问需要交流的,请加入QQ群(579036588),并@骑兔子的龟就可与我联系

END

《SQL优化专栏》

get更多优化技能

(群号:579036588)返回搜狐,查看更多

责任编辑:

mysql 按条件join_MySQL Join竟然可以这么玩?根据条件进行复制相关推荐

  1. mysql join 条件_MySQL Join 竟然可以这么玩?根据条件 进行复制

    大家好,我是知数堂SQL 优化班老师 网名:骑龟的兔子 今天给大家带来, 根据条件进行复制的案例 with t1 as ( select 1 seq ,'AK' id ,'A' type ,'g1' ...

  2. mysql 大数据 join_MySQL JOIN算法原理

    MySQL的JOIN相关操作,是通过"嵌套循环连接算法,NLJ"或者该算法的优化变体"块嵌套循环连接算法,BNLJ"来实现的. ##### 嵌套循环连接算法 两 ...

  3. mysql不用left join_MySQL在右表数据不唯一的情况下使用left join的方法_MySQL - join

    一.Join语法概述join 用于多表中字段之间的联系,语法如下:... FROM table1 INNER|LEFT|RIGHT JOIN table2 ON conditionatable1:左表 ...

  4. mysql 或hive left join不加关联条件

    mysql left join不加关联条件 create table if not exists u1 (id int,name varchar(20) ) ENGINE = MyISAMDEFAUL ...

  5. mysql语法中的join_MySQL JOIN 语法说明与 图解

    一.MySQL JOIN 分类 JOIN 按照功能大致分为如下三类: INNER JOIN(内连接):取得两个表中存在连接匹配关系的记录. LEFT JOIN(左连接):取得左表(table1)完全记 ...

  6. Mysql 优化器内部JOIN算法hash join On-Disk Hash Join Grace Hash Join Hybrid hash join过程详解

    Mysql 各种hash join算法讲解 hash join的概述 提到hash join之前自然得说Nest loop join,以两个表的关联为例,它其实是个双层循环,先遍历外层的表(n条),再 ...

  7. mysql left outer join_关于mysql中的left join和left outer join的区别

    关于mysql中的left join和left outer join的区别 LEFT JOIN是LEFT OUTER JOIN的简写版; 内连接(INNER JOIN) :只连接匹配的行; 左外连接( ...

  8. 【SQL开发实战技巧】系列(六):从执行计划看NOT IN、NOT EXISTS 和 LEFT JOIN效率,记住内外关联条件不要乱放

    系列文章目录 [SQL开发实战技巧]系列(一):关于SQL不得不说的那些事 [SQL开发实战技巧]系列(二):简单单表查询 [SQL开发实战技巧]系列(三):SQL排序的那些事 [SQL开发实战技巧] ...

  9. MySQL查询优化之七-左Join 和右Join 优化(Left Join and Right Join Optimization)

    MySQL查询优化之七-左Join 和右Join 优化(Left Join and Right Join Optimization) 如需转载请标明出处:http://blog.csdn.net/it ...

  10. MySQL 8.0 hash join有重大缺陷?

    我并不这么看. 友情提醒:本文建议在PC端阅读. 徐春阳老师发文爆MySQL 8.0 hash join有重大缺陷. 文章核心观点如下:多表(比如3个个表)join时,只会简单的把表数据量小的放在前面 ...

最新文章

  1. SQL Server基础操作(此随笔仅作为本人学习进度记录七 !--存储过程)
  2. 静态链接库与动态链接库的优缺点
  3. HDU1568 Fibonacci
  4. 小学计算机说课稿,小学信息技术说课稿《新建文件夹》
  5. php二维数组拆分成字符串,PHP二维数组切割为字符串并去除重复的值
  6. 日本語趣味読み 一 星とり
  7. Shell编程入门(第二版)(中)
  8. 信息学奥赛一本通(2041:【例5.9】新矩阵)
  9. c语言做的计算器小程序,c语言实现计算器小程序
  10. 如何零成本录制一首单人ACAPPELLA
  11. Android10支持dcip3,dcip3 相当于多少srgb
  12. 【07月04日】指数估值排名
  13. matlab正态分布概率密度函数,MATLAB绘制正态分布概率密度函数(normpdf)图形
  14. 超简单直观理解懒加载(Lazyload)
  15. box-shadow兼容IE8浏览器写法
  16. mongodb 恢复_MongoDB时间点恢复
  17. 大学计算机专业的同学是怎么学习的?
  18. 微信小程序商城源码独立版/公众号/H5/DIY装修/营销/直播/拼团/秒杀/前端vue全开源代码
  19. HDU6124 Euler theorem
  20. 数据结构课程设计---实现一元稀疏多项式计算器

热门文章

  1. 常见排序算法原理及java实现
  2. HashMap的put过程
  3. webflux之reactor-Publisher
  4. c语言中专业英文词汇的意思,C语言常见英文词汇表
  5. UVA1025 Thematic Contests
  6. 家庭软路由方案:3865U + ESXi6.7(OpenWRTiKuai) + 花生壳蒲公英P5 + 领势MX5300 + 群辉1621 做到国内国外分流、内网设备流控、内网穿透、异地组网
  7. 如何清除计算机的u盘使用记录,如何清除U盘使用痕迹
  8. [转贴]给想立志入行网络或已经初入行的朋友的建议(一)
  9. 北京开通企业登记“e窗通”服务平台 开办企业可3天完成
  10. 概率论与数理统计基础概念与重要定义汇总