Расчет коэффициента роста и удержания с помощью sql - PullRequest
0 голосов
/ 26 мая 2020

Итак, я написал запрос для расчета темпов роста удерживаемых, новых и вернувшихся студентов. Приведенный ниже код возвращает результат, аналогичный этому.

Row  visit_month    student_type    numberofstd  growth 
1      2013          new                574       null
2      2014          new                220       -62%
3      2014        retained             442       245%
4      2015          new                199       -10%
5      2015        retained             533        21%
6      2016          new                214        8%
7      2016        retained             590        11%
8      2016        returning            1         -100%

Запрос, который я пробовал.

with visit_log AS (
    SELECT studentid,
            cast(substr(session, 1, 4) as numeric) as visit_month,
    FROM abaresult
    GROUP BY 1,
             2
    ORDER BY 1,
             2),
  time_lapse_2 AS (
        SELECT studentid,
               Visit_month,
               lag(visit_month, 1) over (partition BY studentid ORDER BY studentid, visit_month) lag
         FROM visit_log),
  time_diff_calculated_2 AS (
        SELECT studentid,
               visit_month,
               lag,
               visit_month - lag AS time_diff
         FROM time_lapse_2),

  student_categorized AS (
        SELECT studentid,
               visit_month,
               CASE
                        WHEN time_diff=1 THEN 'retained'
                        WHEN time_diff>1 THEN 'returning'
                        WHEN time_diff IS NULL THEN 'new'
               END AS student_type,
    FROM time_diff_calculated_2)

SELECT visit_month,
         student_type,
         Count(distinct studentid) as numberofstd,
         ROUND(100 * (COUNT(student_type) - LAG(COUNT(student_type), 1) OVER (ORDER BY student_type)) / LAG(COUNT(student_type), 1) OVER (ORDER BY student_type),0) || '%' AS growth
  FROM student_categorized
group by 1,2
order by 1,2

В приведенном выше запросе рассчитывается коэффициент удержания, новых и возвращаемых на основе цифр последняя сессия student_type category.

Я ищу способ вычислить эти цифры на основе общего количества студентов в каждом visit_month, а не из каждой категории. Есть ли способ добиться этого?

Я пытаюсь получить таблицу, похожую на эту

Row  visit_month    student_type  totalstd  numberofstd  growth 
1      2013          new           574         574       null
2      2014          new           662         220       62%
3      2014        retained        662         442       22%
4      2015          new           732         199       10%
5      2015        retained        732         533       21%
6      2016          new           804         214       8%
7      2016        retained        804         590       11%
8      2016        returning       804         1         100%

Примечание:

totalstd - это общее количество студентов в каждой сессии и получается за счет нового + удержания + возврата.

Расчет роста предполагался.

Пожалуйста, помогите! Спасибо.

1 Ответ

0 голосов
/ 26 мая 2020

Хотя у меня нет ваших исходных данных, я полагаюсь на себя в запросе, которым вы поделились, и в результатах вывода.

Я создал дополнительный код, чтобы вывести желаемый результат. Хочу отметить, что у меня не было доступа к компиляции BigQuery, потому что у меня не было данных. Таким образом, я сам постарался предотвратить возможные ошибки запроса. Кроме того, запросы между ** не изменились и были скопированы из вашего кода. Ниже приведен код (это смесь вашего и дополнительных битов, которые я создал):

#*****************************************************************
with visit_log AS (
    SELECT studentid,
            cast(substr(session, 1, 4) as numeric) as visit_month,
    FROM abaresult
    GROUP BY 1,
             2
    ORDER BY 1,
             2),
  time_lapse_2 AS (
        SELECT studentid,
               Visit_month,
               lag(visit_month, 1) over (partition BY studentid ORDER BY studentid, visit_month) lag
         FROM visit_log),
  time_diff_calculated_2 AS (
        SELECT studentid,
               visit_month,
               lag,
               visit_month - lag AS time_diff
         FROM time_lapse_2),

  student_categorized AS (
        SELECT studentid,
               visit_month,
               CASE
                        WHEN time_diff=1 THEN 'retained'
                        WHEN time_diff>1 THEN 'returning'
                        WHEN time_diff IS NULL THEN 'new'
               END AS student_type,
    FROM time_diff_calculated_2)
#**************************************************************

#Code I added
#each unique visit_month will have its count
WITH total_stud AS (
SELECT visit_month, count(distinct studentid) as totalstd FROM visit_log 
GROUP BY 1
ORDER BY visit_month
),

#After you have your student_categorized temp table, create another one
#It will have the count of the number of students per visit_month per student_type
number_std_monthType AS (
SELECT visit_month,student_type, Count(distinct studentid) as numberofstd from student_categorized
GROUP BY 1, 2
),

#You will have one row per combination of visit_month and student_type
student_categorized2 AS(
SELECT DISTINCT visit_month,student_type FROM student_categorized2 
GROUP BY 1,2
),

#before calculation, create the table with all the necessary data
#you have the desired table without the growth
#notice that I used two keys to join t1 and t3 so the results are correct
final_t AS (
SELECT t1.visit_month, 
       t1.student_type, 
       t2.totalstd as totalstd, 
       t3.numberofstd 
FROM student_categorized2 t1 
       LEFT JOIN total_stud AS t2 ON t1.visit_month = t2.visit_month
       LEFT JOIN number_std_monthType t3 ON (t1.visit_month = t3.visit_month and t1.student_type = t3.student_type)
ORDER BY
)

#Now all the necessary values to calculate growth are in the temp table final_t
SELECT visit_month, student_type, totalstd, numberofstd,
       ROUND(100 * (totalstd - LAG(totalstd) OVER (PARTITION BY visit_month ORDER BY visit_month ASC) /LAG(totalstd) OVER (PARTITION BY visit_month ORDER BY visit_month ASC) || '%' AS growth
FROM final_t  

Обратите внимание, что я использовал LEFT JOIN , чтобы иметь правильные подсчеты в финальном таблица, после того, как каждый счет был рассчитан в другой временной таблице . Кроме того, я не использовал ваш последний оператор SELECT.

Если у вас возникнут проблемы с кодом, не стесняйтесь спрашивать.

...