内部联接平均值的MYSQL MIN

时间:2017-02-27 13:57:15

标签: mysql sql

鉴于有两个表:

  • 活动
  • 用户

每个user都可以有一个或多个事件。

每个event只能由一个用户拥有。

我将以下查询放在一起,以平均事件和用户的相应created_at时间戳之间的差异。

SELECT 
(
    SELECT AVG(TIMESTAMPDIFF(DAY, users.created_at, events.created_at))
    FROM users
    INNER JOIN events
    ON users.id = events.user_id
    WHERE events.created_at IS NOT NULL
    AND users.created_at IS NOT NULL
) AS "Difference between created_at of user and created_at of user's first event, averaged across all users."

然而,如何只包括FIRST重叠,其中event.created_at的时间戳最低?我相信目前,代码将采用每个时间戳和created_at之间的差异,并将其平均。我想要完成的是为每个用户在他/她的第一个创建的事件之间获得差异,为数据库中的每个用户执行此操作,并对结果进行平均。

解决方案可能很简单,但我无法提出有效的查询。

感谢任何帮助或建议!

3 个答案:

答案 0 :(得分:2)

我认为您需要一个子查询来查找最早的事件,以便在事件加入中获得一行......这样的事情?

SELECT AVG(TIMESTAMPDIFF(DAY, u.created_at, e.created_at))
FROM users u
INNER JOIN events e ON u.id = e.user_id
INNER JOIN
(
    SELECT user_id, MIN(created_at) minDate
    FROM events
    GROUP BY user_id
) m 
ON m.user_id = u.user_id AND e.created_at = m.minDate
WHERE e.created_at IS NOT NULL AND u.created_at IS NOT NULL

如果不清楚,我在那里完成的是你的原始连接为每个用户提供所有事件,但是这会针对每个用户的最早事件加入,所以我们最终每个用户只有一行谁至少有一次活动。

这可以简化,因为我们不需要首先加入对抗事件,我们可以只是加入用户来反对该子查询......

SELECT AVG(TIMESTAMPDIFF(DAY, u.created_at, m.minDate))
FROM users u
INNER JOIN
(
    SELECT user_id, MIN(created_at) minDate
    FROM events
    GROUP BY user_id
) m 
ON m.user_id = u.user_id
WHERE u.created_at IS NOT NULL

答案 1 :(得分:1)

使用子查询获取第一个事件的时间(使用MIN()而不是AVG())。然后取外部查询中的平均值:

SELECT AVG(x.TimeToFirstEvent)
FROM (SELECT MIN(TIMESTAMPDIFF(DAY, u.created_at, e.created_at)) as TimeToFirstEvent
      FROM users u INNER JOIN
           events e
           ON u.id = e.user_id
      WHERE e.created_at IS NOT NULL AND
            u.created_at IS NOT NULL AND
            e.created_at >= u.created_at  -- probably not needed
      GROUP BY u.id
     ) x;

答案 2 :(得分:0)

这是一个简短的方法:

SELECT AVG(TIMESTAMPDIFF(DAY, u.created_at, 
    (SELECT MIN(e.created_at) FROM events WHERE e.user_id = u.id)
))
FROM users u

请注意,AVG()将排除所有NULL值,此处不需要条件created_at IS NOT NULL