“ 上一篇文章的介绍,2500字干货分享:带你摆脱SQL零基础,相信大家会对sql有了更清晰的认知。学习是一个漫长的过程,不过今天还是介绍几个实例的sql写法,让大家在必要的时候直接利用上,不必因为数据处理耽误太长时间。”
01-行列转换
1. 行转列
先观察下面的两组数据,左侧每个用户购买了多个品类,数据记录了多行,假设在表名为table_a中。右侧区域每个用户的购买的品类都汇总到了一个单元格内,如何实现,不同数据库内sql有着不同的写法:
- MySQL:
- 使用函数:group_concat
- 语法结构:group_concat(distinct 合并字段 order by ASC/DESC 排序字段] [Separator '分隔符'])
- 语句:
- select 用户编号, group_concat(distinct 购买品类 order by 购买品类 asc Separator ',')from table_a group by 用户编号
- HIVE:
- 使用函数:concat_ws与concat_set/concat_list结合
- 语法结构:concat_ws(分隔符号,concat_set(要合并的字段)),set有去重功能,list没有
- 语句:
- select 用户编号, concat_ws(',',concat_set(购买品类)from table_a group by 用户编号
- Oracle:很久以前写的,有些麻烦,参考下就好,现在应该有简便写法了。
- 使用函数:SYS_CONNECT_BY_PATH
- 语法结构:
- 语句:
- SELECT 用户编号, SUBSTR (MAX(SYS_CONNECT_BY_PATH (购买品类,',')),2) 购买品类FROM(SELECT 用户编号, 购买品类, rn, LEAD (rn) OVER(PARTITION BY id ORDER BY rn) rn1 FROM(SELECT 用户编号, 购买品类, ROW_NUMBER () OVER(ORDER BY 购买品类) rn FROM table))START WITH rn1 IS NULLCONNECT BY rn1=PRIOR rn GROUP BY 用户编号;
2. 列转行
接下来,来思考如何变换回去,其他的数据库暂不举例了,很久不用了,介绍个hive sql的函数用法:
- HIVE:
- 使用函数:explode
- 语法结构:lateral view explode ...
- 语句:
select 用户编号,购买品类1from(select 用户编号
from(select 用户编号, split(购买品类,',') 购买品类0
from table_a ) t
lateral view explode (购买品类0) t as 购买品类1)t2
02
有关分组排序
1. ** over(partition by ** order by **)的用法
over前可支持函数还是很多的,比如lead、lag、sum、count、avg、first_value、last_value、ratio_to_report、percent_rank等,不过本部分只是让大家了解这个语法结构,这些函数我们放在之后文章里详细介绍用法。接下来通过下面这组数据进行举例说明:
案例:每个人最早购买时间的购买品类、时间、用户编号
select 用户编号,购买品类,购买时间from (select 用户编号,购买品类,购买时间,
row_number() over(partition by 用户编号 order by 购买时间 asc) rn
from table_a) where rn=1
这里借助的是row_number函数,与此函数作用类似的还有rank,dense_rank等,三者的差异很好理解,顺便在这里介绍下与row_number一起三者的区别:
row_number得到1,2,3,4,5,...
rank得到1,1,3,4,4,6,...
dense_rank得到1,1,2,3,4,4,5,...
今天先介绍下这里,更多精彩内容关注更新~
分享是一种快乐