【MySQL】计算时间段内满足是首次登录的用户(根据时间统计首次登录用户人数)

力扣题

1、题目地址

1107. 每日新用户统计

2、模拟表

Traffic 表:

Column NameType
user_idint
activityenum
activity_datedate
  • 该表可能有重复的行。
  • activity 列是 ENUM 类型,可能取 (‘login’, ‘logout’, ‘jobs’, ‘groups’, ‘homepage’) 几个值之一。

3、要求

  • 编写解决方案,找出从今天起最多 90 天内,每个日期该日期首次登录的用户数。假设今天是 2019-06-30 。
  • 以 任意顺序 返回结果表。

4、示例

输入:

Traffic 表:

user_idactivityactivity_date
1login2019-05-01
1homepage2019-05-01
1logout2019-05-01
2login2019-06-21
2logout2019-06-21
3login2019-01-01
3jobs2019-01-01
3logout2019-01-01
4login2019-06-21
4groups2019-06-21
4logout2019-06-21
5login2019-03-01
5logout2019-03-01
5login2019-06-21
5logout2019-06-21

输出:

login_dateuser_count
2019-05-011
2019-06-212

解释:

请注意,我们只关心用户数非零的日期.
ID 为 5 的用户第一次登陆于 2019-03-01,因此他不算在 2019-06-21 的的统计内。

5、代码编写

要求分析

我们是要查询出 2019-06-30 的最近 90 天(包括 90 天)的首次登录用户,有四种情况

  1. 最近 90 天只出现一次登录,90天以外没有,查询出来就是首次登录时间
  2. 最近 90 天只出现一次登录,90天以外也出现登录,查询不出来
  3. 最近 90 天出现多次登录,90天以外没有,需要进行筛选查询出 最小时间 那个才是首次登录时间
  4. 最近 90 天出现多次登录,90天以外也出现登录,查询不出来

第一种写法

SELECT login_date, COUNT(one.user_id) AS user_count
FROM (
    SELECT user_id, MIN(activity_date) AS login_date
    FROM Traffic
    WHERE activity = 'login'
    AND activity_date >= DATE_SUB('2019-06-30', INTERVAL 90 DAY)
    AND user_id NOT IN (
    	SELECT user_id 
    	FROM Traffic 
    	WHERE activity = 'login' 
    	AND activity_date < DATE_SUB('2019-06-30', INTERVAL 90 DAY)
    )
    GROUP BY user_id
) AS one
GROUP BY login_date

代码分析:

  • 查询最近 90 天
activity_date >= DATE_SUB('2019-06-30', INTERVAL 90 DAY)
  • 将最近 90 天以外的进行排除,对应 要求分析 里面的 2 和 4 的情况
user_id NOT IN (
	SELECT user_id 
	FROM Traffic 
	WHERE activity = 'login' 
	AND activity_date < DATE_SUB('2019-06-30', INTERVAL 90 DAY)
)
  • 对应 要求分析 里面的 1 和 3 情况,主要是 3 情况
MIN(activity_date)

第二种写法(理解要求简化写法)

SELECT login_date, COUNT(one.user_id) AS user_count
FROM (
    SELECT user_id, MIN(activity_date) AS login_date
    FROM Traffic
    WHERE activity = 'login'
    GROUP BY user_id
    HAVING login_date >= DATE_SUB('2019-06-30', INTERVAL 90 DAY)
) AS one
GROUP BY login_date

代码分析:

  • 首先找出各个用户的首次登录时间
SELECT user_id, MIN(activity_date) AS login_date
FROM Traffic
WHERE activity = 'login'
GROUP BY user_id
  • 再看哪些是满足最近90天内的
SELECT user_id, MIN(activity_date) AS login_date
FROM Traffic
WHERE activity = 'login'
GROUP BY user_id
HAVING login_date >= DATE_SUB('2019-06-30', INTERVAL 90 DAY)
  • 11
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值