Problem
+---------------+---------+
| Column Name | Type |
+---------------+---------+
| user_id | int |
| session_id | int |
| activity_date | date |
| activity_type | enum |
+---------------+---------+
Write an SQL query to find the average number of sessions per user for a period of 30 days ending 2019-07-27 inclusively, rounded to 2 decimal places. The sessions we want to count for a user are those with at least one activity in that time period.
Solution
Method 1 - Using CTEs
Code
Sql
WITH myquery AS
(
SELECT user_id,
session_id
FROM Activity
WHERE activity_date BETWEEN '2019-06-28' AND '2019-07-27'
GROUP BY user_id, session_id
)
SELECT
IFNULL(ROUND(COUNT(*) / COUNT(DISTINCT user_id), 2), 0.00) average_sessions_per_user
FROM myquery;
Again, not the best solution.
Method 2 - Using Mathematical functions
Code
Sql
Here’s a better example:
SELECT ifnull(ROUND(COUNT(DISTINCT session_id) / COUNT(DISTINCT user_id), 2), 0.00)
AS average_sessions_per_user
FROM Activity
WHERE activity_date >= '2019-06-28' and activity_date <= '2019-07-27';
This example is better, although maybe it could have used BETWEEN
. It’s more simple than my solution, simply dividing all distinct Session IDs and dividing by all distinct User IDs.
I have a strange habit of over complicating things.