升级“脚本小子”

脚本小子

脚本小子并不自己写代码,而是四处 copy 代码。还有的情况是 copy 自己写的代码。

如何做的更好写

再写 sql 的时候,注意总结解决一类问题的通用方法。单纯 copy 代码,不如封装函数。copy 相似逻辑的代码,不如重写逻辑。

使用 git log --since='2019-12-25' -p file 对提交的 git 日志进行分析。找出做了哪些修改。我在写 sql 的时候,每修改一次基脚本,
就 add commit 一次,然后到服务器上测试代码。这样做的好处是,能够记录下来每次做了哪些修改,也能发现 sql 常犯的错误。

hive CET 语法的 bug

cet 语法增强 DML 语句的可读性。但是也会有一些问题。

  • 子查询中的字段类型的时候,on 上的条件失效,即使 cast 类型转换后也会保存。
  • 子查询 join 后,grouping set 语法做计算后,有些 group__id 下的数值统计错误
  • 使用子查询做 union all 操作后,会出现 hive 系统的中间表不存在的错误。

这些错误解决起来也简单,一方面可以向 hive 社区提交 bug ,但是哪里的反应失效可能会比较差。另一方面,我们可以绕过这个坑,将自查的内容些到中间表里面,然后再进行关联后,将结果保存到目标表中。例如

with sub_query1 as (
  select ... from ... where ...
),sub_query2 as (
  select ... from ... where ...
), ...
,sub_queryN as (
  select ... from ... where ...
)
insert overwrite table target_table
select ...
  from sub_query join
  where ...

如果遇到上述问题,可以如下改造。

create table sub_query1 
as
  select ... from ... where ...
;
create table sub_query2
as 
  select ... from ... where ...
;
 ...
create table sub_queryN 
as
select ... from ... where ...
;
insert overwrite table target_table 
select ...
  from sub_query join
  where ...

开窗函数陷阱

开窗函数在做子集计算聚合计算的时候是非常好用的,但是会有一个问题,请看下面的例子:

门店交易日期外卖份数
A2020年2月3日50
A2020年2月10日50
A2020年2月11日50
A2020年2月27日50

这里有个需求是,要统计出月至今的每天的外卖份数。

select trade_date
      ,shop_name 
      ,sum(sale_copy) over(partition by trade_date , shop_name) as sale_copy
 from fct_sale

得到的结果是这样的:

|trade_date|shop_name|sale_copy |
| A| 2020年2月3日| 50 |
| A| 2020年2月10日| 100 |
| A| 2020年2月11日| 150 |
| A| 2020年2月27日| 200 |

这里有个问题是在 2020年2月4日 ~ 2020年2月4日这些天内,A 门店没有销售记录,那就不会有累加的销售量。有一个解决办法,我们需要一个维表 trede_date_shop。

日期门店
2020年2月1日A
2020年2月2日A
2020年2月3日A
2020年2月4日A
2020年2月5日A
2020年2月6日A
2020年2月7日A
2020年2月8日A
2020年2月9日A

有了这个维表,query 写成下面的样子了:

     select a.trade_date
           ,a.shop_name 
           ,sum(coalesce(sale_copy,0)) over(partition by a.trade_date , a.shop_name ) as sale_copy
       from trede_date_shop as a 
  left join fct_sale as b
         on a.trade_date = b.trade_date
        and a.shop_name = b.shop_name 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值