SQL 交易归因

SQL Transaction Attribution

我需要根据不同的回顾提取已交易的用户总数 windows。

首先,我有一个 table 这样的:

user_id     date        action
1           2018/01/01  click
3           2018/01/01  view
5           2018/01/01  click
1           2018/01/02  view
1           2018/01/02  view
3           2018/01/03  click
2           2018/01/05  click
1           2018/01/05  transact
3           2018/01/05  transact
2           2018/01/06  view
1           2018/01/06  click
3           2018/01/06  view
2           2018/01/08  transact
2           2018/01/08  click
1           2018/01/08  click
1           2018/01/09  click
4           2018/01/09  click
3           2018/01/12  view
4           2018/01/12  transact
3           2018/01/13  view
5           2018/01/13  transact
4           2018/01/15  view
5           2018/01/15  click
4           2018/01/16  view
2           2018/01/17  transact
5           2018/01/18  click

从这里开始,我想我需要提取在交易操作之前发生的最后一个非交易日期和操作以及自上次操作以来的天数。那么 table 看起来像这样:

user_id     date        action      prevdate_nontrans       prev_nontrans_action        days_since
1           2018/01/01  click           
3           2018/01/01  view            
5           2018/01/01  click           
1           2018/01/02  view            
1           2018/01/02  view            
3           2018/01/03  click           
2           2018/01/04  click           
1           2018/01/05  transact    2/01/2018               view                        3
3           2018/01/05  transact    3/01/2018               click                       2
2           2018/01/06  view            
1           2018/01/06  click           
3           2018/01/06  view            
2           2018/01/08  transact    5/01/2018               click                       3
2           2018/01/08  click           
1           2018/01/08  click           
1           2018/01/09  click           
4           2018/01/09  click           
3           2018/01/12  view            
4           2018/01/12  transact    9/01/2018               click                       3
3           2018/01/13  view            
5           2018/01/13  transact    1/01/2018               click                       12
4           2018/01/15  view            
5           2018/01/15  click           
4           2018/01/16  view            
2           2018/01/17  transact    8/01/2018               click                       9
5           2018/01/18  click       

使用它,我希望构建一个 table 来显示每周执行任何非交易操作的用户总数和基于交易的用户总数的每周细分在不同的回顾 windows。例如:

date (weekly)       total   1-day lookback  2-day lookback  3-day lookback
1/01/2018           4       0               1               3
8/01/2018           5       0               0               1
15/01/2018          3       0               0               0

从 1 月 1 日开始的那一周,用户 ID 1、2、3 和 5 进行了非交易操作,导致总数为 4。根据 1 天的交易回溯,未找到任何用户。根据 2 天的回溯,发现用户 ID 3 在 table 上的结果为 1。基于 3 天的回溯,发现用户 ID 3,1 和 2 在 table.

上结果为 3

回溯列下的计数将基于非交易操作发生的时间 - 解释为什么用户 id 2 在 1 月 8 日的交易被归因于 1 月 1 日那一周(3 天回溯)。

作为参考,我正在使用 Athena 构建 tables。根据操作类型进一步分割数据最终会很重要,所以如果您对此有任何想法,那也很好。

我使用下面的查询来实现您的结果,但日期列数据类型必须是 DATETIME,操作列应该是 INT 并参考 action_id(action table) 以获得更好的性能。

CREATE TABLE user_action(user_id BIGINT, Date DATE, action VARCHAR(100)); 

INSERT INTO user_action(user_id, Date, action)
VALUES
(1,'2018/01/01', 'click'),
(3,'2018/01/01',  'view'),
(5,'2018/01/01',  'click'),
(1,'2018/01/02',  'view'),
(1,'2018/01/02',  'view'),
(3,'2018/01/03',  'click'),
(2,'2018/01/05',  'click'),
(1,'2018/01/05',  'transact'),
(3,'2018/01/05',  'transact'),
(2,'2018/01/06',  'view'),
(1,'2018/01/06',  'click'),
(3,'2018/01/06',  'view'),
(2,'2018/01/08',  'transact'),
(2,'2018/01/08',  'click'),
(1,'2018/01/08',  'click'),
(1,'2018/01/09',  'click'),
(4,'2018/01/09',  'click'),
(3,'2018/01/12',  'view'),
(4,'2018/01/12',  'transact'),
(3,'2018/01/13',  'view'),
(5,'2018/01/13',  'transact'),
(4,'2018/01/15',  'view'),
(5,'2018/01/15',  'click'),
(4,'2018/01/16',  'view'),
(2,'2018/01/17',  'transact'),
(5,'2018/01/18',  'click');

SELECT ua.*, ROW_NUMBER() OVER(PARTITION BY user_id order by date, action) as ranks
INTO #temp
FROM user_action ua
order by user_id, ranks;

select t1.*, t2.date, t2.action, DATEDIFF(DAY, t2.date, t1.date)
from #temp t1
LEFT JOIN #temp t2 ON t1.user_id = t2.user_id AND t2.action IN ('view','click') and t1.action = 'transact' and (t1.ranks-1) = t2.ranks
order by t1.user_id, t1.ranks;