diff --git a/mnoskov/postgresql/5. Функции: даты, строки, логика/DQL_functions_practice.sql b/mnoskov/postgresql/5. Функции: даты, строки, логика/DQL_functions_practice.sql new file mode 100644 index 0000000..f37e1ef --- /dev/null +++ b/mnoskov/postgresql/5. Функции: даты, строки, логика/DQL_functions_practice.sql @@ -0,0 +1,90 @@ +-- Задание 1 +SELECT + name, + created_at::date, + current_date - created_at::date AS days_since_registration +FROM + mnoskov.users +WHERE + is_active = TRUE + AND current_date - created_at::date > 180 +ORDER BY + days_since_registration desc; +-- Очень старым пользователям можно кинуть рассылку на почту на подобии 'Представляете, мы вместе уже 777 дней, вот вам купон на скидку' +-- Удобнее вычитать ::date, чтобы days_since_registration красиво выглядел в таблице + + +-- Задание 2 +SELECT + name, + lower(email) AS email_clean, + substring(email FROM POSITION('@' IN email) + 1) AS domain +FROM + mnoskov.users +WHERE email IS NOT NULL +ORDER BY domain, name; +-- email приводят к нижнему регистру для нормализации записи, а зачем выделяют домен не понимаю, может быть для аналитики по типу кто какой почтой пользуется +-- Получу NULL в domain + + +-- Задание 3 +SELECT + name, + age, + CASE + WHEN age < 25 THEN 'young' + WHEN age BETWEEN 25 AND 35 THEN 'adult' + WHEN age > 35 THEN 'senior' + END AS age_group +FROM + mnoskov.users +ORDER BY + age; +-- Почему удобнее держать логику сегментации в SQL (CASE), а не только в коде приложения? Я не понял этот вопрос. +-- Если забыть в ветку ELSE, то будет NULL у тех кто никуда не попал + + +-- Задание 4 +SELECT + name, + created_at::date, + current_date - created_at::date AS days_since_registration, + CASE + WHEN created_at >= current_date - INTERVAL '30 days' THEN 'hot' ELSE 'regular' + END AS hot_flag +FROM + mnoskov.users +WHERE + created_at >= current_date - INTERVAL '30 days'; +-- Фильтрация по дате в WHERE исключает неподходящие варианты, а простой CASE в нашем случае возвращает результат в виде двух вариантов - подошло/не подошло и эти оба варианта остаются в таблице +-- Стоит запускать какие нибудь привлекательные варианты со скидкам и акциями, чтобы удержать пользователся + + +-- Задание 5 +SELECT + count(*) AS total_users, + count(email) AS with_email, + count(*) - count(email) AS without_email, + ((count(*) - count(email))::float / count(*)) * 100.0 AS percent_without_email +FROM + mnoskov.users; +-- Агрегаты дают более точную информацию чем просто на глаз +-- Я бы предолжил запустить активно вылезающие блоки с предложением зарегестрироваться, или же запретить пользоваение продуктом без регистрации + + +-- Задание 6 +SELECT + name, + current_date - created_at::date AS days_since_registraion, + CASE + WHEN current_date - created_at::date <= 30 THEN 'new' + WHEN current_date - created_at::date BETWEEN 31 AND 180 THEN 'middle' + WHEN current_date - created_at::date > 180 THEN 'old' + END AS tenure_group, + is_active +FROM + mnoskov.users +ORDER BY + tenure_group, days_since_registraion; +-- Сегментация по стажу говорит о опыте человека, а по возрасту только о возрасте +-- Пересчитывать каждый день - плюсы: не занимает места на диске, минусы: тратит больше вычислительных ресурсов, а если хранить статическое поле, то все наоборот \ No newline at end of file