题解 | SQL 167. 连续签到领金币

连续签到领金币

https://www.nowcoder.com/practice/aef5adcef574468c82659e8911bb297f

WITH t1 AS( -- t1表筛选出活动期间内的数据,并且为了防止一天有多次签到活动,distinct 去重
	SELECT
		DISTINCT uid,
		DATE(in_time) dt,
		DENSE_RANK() over(PARTITION BY uid ORDER BY DATE(in_time)) rn -- 编号
	FROM
		tb_user_log
	WHERE
		DATE(in_time) BETWEEN '2021-07-07' AND '2021-10-31' AND artical_id = 0 AND sign_in = 1
),
t2 AS ( # t2 就是求出
	SELECT
	*,
	DATE_SUB(dt,INTERVAL rn day) dt_tmp,
	DENSE_RANK() over(PARTITION BY DATE_SUB(dt,INTERVAL rn day),uid ORDER BY dt ) AS new_num,
	case DENSE_RANK() over(PARTITION BY DATE_SUB(dt,INTERVAL rn day),uid ORDER BY dt )%7 -- 再次编号
		WHEN 3 THEN 3
		WHEN 0 THEN 7
		ELSE 1
	END as day_coin -- 用户当天签到时应该获得的金币数
	FROM
	t1
),
t3 AS (SELECT uid,
              DATE_FORMAT(dt, '%Y%m') `month`,
              sum(day_coin)           coin -- 总金币数
       FROM t2
       GROUP BY uid, DATE_FORMAT(dt, '%Y%m')
       ORDER BY DATE_FORMAT(dt, '%Y%m'), uid
)
SELECT * FROM t3;

# 这道题的关键在于,减差后的时间,id才是排序分类基准点,排序照常按照dt时间!

全部评论

相关推荐

05-29 22:11
门头沟学院 Java
Elastic90:抛开学历造假不谈,这公司的招聘需求也挺怪的,Java开发还要求你有图文识别、移动端开发和c++的经验,有点逆天了。
点赞 评论 收藏
分享
码农索隆:单休一个月少休息4天,一年就是48天,平时节假日,别人3天假期,单休的两天
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务