#python #apache-spark #pyspark #apache-spark-sql
#python #apache-spark #pyspark #apache-spark-sql
Вопрос:
У меня есть простой фрейм данных Spark, в котором хранятся квартальные итоги с начала 2020 года.
| id | year | quarter | yq | total |
|:---:|:----:|:-------:|:------:|:------:|
| 1 | 2020 | 1 | 202001 | 23 |
| 1 | 2020 | 2 | 202002 | 3545 |
| 1 | 2020 | 3 | 202003 | 3 |
| 1 | 2020 | 4 | 202004 | 5345 |
| 1 | 2021 | 1 | 202101 | 3534 |
| 2 | 2020 | 1 | 202001 | 567 |
| 2 | 2020 | 2 | 202002 | 35 |
| 2 | 2020 | 3 | 202003 | 989 |
| 2 | 2020 | 4 | 202004 | 78786 |
| 2 | 2021 | 1 | 202101 | 321 |
| ... | .. | ... | ... | ... |
Как я могу сравнить разницу в% между текущим кварталом и тем же кварталом предыдущего года?
Ожидаемый результат:
| id | yq | growth_over_same_quarter_in_previous_year |
|-----|--------|-------------------------------------------|
| 1 | 202101 | 197 |
| 2 | 202101 | -55 |
| ... | ... | ... |
Ответ №1:
Вы можете использовать lag
для сравнения с предыдущим кварталом того же года для того же идентификатора.
from pyspark.sql import functions as F, Window
last_year = F.lag('total').over(Window.partitionBy('id', 'quarter').orderBy('year'))
df2 = df.withColumn(
'change',
(F.col('total') - last_year) / last_year * 100
).filter('change is not null').select('id', 'yq', 'change')
df2.show()
--- ------ -------------------
| id| yq| change|
--- ------ -------------------
| 1|202101| 15265.217391304346|
| 2|202101|-43.386243386243386|
--- ------ -------------------
Комментарии:
1. Какова цель фильтра здесь? Чтобы учесть 0 изменений?
2. Для случая, если предыдущей строки нет (например, yq = 202001), where
lag
вернет null, и поэтомуchange
также будет null @Someguywhocodes