1. 程式人生 > 實用技巧 >大資料實戰(三十八):電商數倉(三十一)之使用者行為資料倉庫(十七)連續主題

大資料實戰(三十八):電商數倉(三十一)之使用者行為資料倉庫(十七)連續主題

1 最近連續三周活躍使用者數

最近3周連續活躍的使用者:通常是週一對前3周的資料做統計,該資料一週計算一次。

1.1 DWS層

使用周活明細表dws_uv_detail_wk作為DWS層資料

1.2 ADS層

1)建表語句

hive (gmall)>
drop table if exists ads_continuity_wk_count;
create external table ads_continuity_wk_count( 
    `dt` string COMMENT '統計日期,一般用結束週週日日期,如果每天計算一次,可用當天日期',
    `wk_dt` string COMMENT '持續時間',
    `continuity_count` bigint
) 
row format delimited fields terminated by '\t'
location '/warehouse/gmall/ads/ads_continuity_wk_count';
View Code

2)

=============================主題 最近連續三週活躍使用者數=========================
連續三週後躍使用者: 在當前日期之前三週的周活表中,此使用者都存在!
周活表特點按照mid_id進行了去重!
因此如果使用者,在連續三週的周活中出現,那麼就會有3條對應的記錄!
-----------------------------需求-----------------------
-----------------------------相關表---------------------
周活表:dws_dv_detail_wk
-----------------------------思路-----------------------

求當前日期,之前三週的資料。根據mid分組,分組後統計組內記錄數量
=3,即是連續三週登入的使用者
-----------------------------SQL------------------------
insert into table ads_continuity_wk_count
select
'2020-02-18',
concat(date_sub(next_day('2020-02-18','mo'),21),'-',date_sub(next_day('2020-02-18','mo'),1)),
count(*)
from
(select
mid_id
from dws_uv_detail_wk
where monday_date BETWEEN date_sub(next_day('2020-02-18','mo'),21)
and '2020-02-18'
group by mid_id
having count(*)=3) tmp

1.3 編寫指令碼

ads_continuity_wk_log.sh

#!/bin/bash
if [ -n "$1" ]
then
     do_date=$1
else
    do_date=$(date -d yesterday +%F)
fi

echo ===日誌日期為$do_date===


sql="

use gmall;
insert into table ads_continuity_wk_count
select 
    '$do_date',
    concat(date_sub(next_day('$do_date','mo'),21),'-',date_sub(next_day('$do_date','mo'),1)),
    count(*)
from    
(select 
    mid_id
from dws_uv_detail_wk
where monday_date BETWEEN date_sub(next_day('$do_date','mo'),21)
and '$do_date'
group by mid_id
having count(*)=3) tmp
"
hive  -e "$sql"

2最近七天內連續三天活躍使用者數

說明:最近7天內連續3天活躍使用者數

2.1 DWS層

使用日活明細表dws_uv_detail_day作為DWS層資料

2.2 ADS層

1)建表語句

hive (gmall)>
drop table if exists ads_continuity_uv_count;
create external table ads_continuity_uv_count( 
    `dt` string COMMENT '統計日期',
    `wk_dt` string COMMENT '最近7天日期',
    `continuity_count` bigint
) COMMENT '連續活躍裝置數'
row format delimited fields terminated by '\t'
location '/warehouse/gmall/ads/ads_continuity_uv_count';
View Code

2)

-----------------------------需求 最近七天內連續三天活躍使用者數-----------------------
-----------------------------相關表---------------------
日活表: dws_uv_detail_day
-----------------------------思路-----------------------
連續:
假如A列,以X遞增,以a開頭
假如B列,以Y遞增,以b開頭

A B 連續兩列差值
a b b-a
a+X b+y b-a + (Y-x)
a+2X b+2y b-a + 2(y-X)

假如A,B列都是連續的,有規律遞增,那麼每兩列之間的差值,也是以 Y-X遞增。
加入X=Y,此時每兩列之間的差值,以0遞增,差值一樣!

思路:①取當前日誌之前7天的資料
②按照使用者mid_id分組,按照日期進行升序排序
③使用rownumber函式,建立一個連續遞增的列
④講日期列和rw列,進行做差
⑤講使用者和差值進行分組,組內至少有3條記錄,將複合條件的mid_id進行過濾即可
-----------------------------SQL------------------------
insert into TABLE ads_continuity_uv_count
select
'2020-02-18',
concat(date_sub('2020-02-18',7),'-','2020-02-18'),
count(DISTINCT mid_id)
from
(select
mid_id
from
(SELECT
mid_id,dt,ROW_NUMBER() over(PARTITION by mid_id order by dt )rn,
date_sub(dt,ROW_NUMBER() over(PARTITION by mid_id order by dt )) diff
from dws_uv_detail_day
where dt BETWEEN date_sub('2020-02-18',7) and '2020-02-18') tmp
GROUP by mid_id,diff
having count(*)>=3 ) tmp2

3 編寫指令碼

ads_continuity_log.sh

#!/bin/bash
if [ -n "$1" ]
then
     do_date=$1
else
    do_date=$(date -d yesterday +%F)
fi

echo ===日誌日期為$do_date===


sql="

use gmall;
insert into TABLE ads_continuity_uv_count
select 
    '$do_date',
    concat(date_sub('$do_date',7),'-','$do_date'),
    count(DISTINCT mid_id)
from
(select 
    mid_id
from
(SELECT 
    mid_id,dt,ROW_NUMBER() over(PARTITION by mid_id order by dt  )rn,
    date_sub(dt,ROW_NUMBER() over(PARTITION by mid_id order by dt  )) diff
from dws_uv_detail_day
where dt BETWEEN date_sub('$do_date',7) and '$do_date') tmp
GROUP by mid_id,diff
having count(*)>=3 ) tmp2
"
hive  -e "$sql"