pyspark-将具有最大值的列转换为单独的1和0条目

ttp71kqs  于 2021-07-09  发布在  Spark
关注(0)|答案(1)|浏览(537)

我有一个在Pandas这个问题的工作版本,但我有麻烦把它翻译成Pypark。
我的输入数据框如下所示:

test_df = pd.DataFrame({
    'id': [1],
    'cat_1': [2],
    'cat_2': [2],
    'cat_3': [1]
})
test_df_spark = spark.createDataFrame(test_df)
test_df_spark.show()

+---+-----+-----+-----+
| id|cat_1|cat_2|cat_3|
+---+-----+-----+-----+
|  1|    2|    2|    1| <- non-maximum
+---+-----+-----+-----+
         ^     ^
         |     |
     maximum maximum

我想:
获取类别1、类别2、类别3中具有最大值的列(1或更多)。在本例中,它们将是cat\ 1和cat\ 2。
这些列的值应为1。其余非最大列将设置为0。
值为1的列应划分为单独的行。
结果Dataframe应如下所示:

+---+-----+-----+-----+
| id|cat_1|cat_2|cat_3|
+---+-----+-----+-----+
|  1|    1|    0|    0|
|  1|    0|    1|    0|
+---+-----+-----+-----+

目前,我能弄清楚的最多的是如何根据列的值(无论是否为最大值)将列设置为1或0,但我仍然缺少如何生成其他条目:

columns = ['cat_1', 'cat_2', 'cat_3']
(
    test_df_spark
    .withColumn(
        'max_value',
        F.greatest(
            *columns
        )
    )
    .select(
        'id',
        *[F.when(F.col(c) == F.col('max_value'), F.lit(1)).otherwise(F.lit(0)).alias(c) for c in columns]
    )
    .show()
)

+---+-----+-----+-----+
| id|cat_1|cat_2|cat_3|
+---+-----+-----+-----+
|  1|    1|    1|    0|
+---+-----+-----+-----+

提前谢谢!

uurity8g

uurity8g1#

假设你现在的结果是 df1 :

columns = ['cat_1', 'cat_2', 'cat_3']
df1 = (
    test_df_spark
    .withColumn(
        'max_value',
        F.greatest(
            *columns
        )
    )
    .select(
        'id',
        *[F.when(F.col(c) == F.col('max_value'), F.lit(1)).otherwise(F.lit(0)).alias(c) for c in columns]
    )
)

你可以操纵 df1 通过创建一个结构数组和 inline 信息技术:

df2 = df1.select(
    'id', 
    F.array(*[
        F.when(
            F.col(c1) == 1, 
            F.struct(*[
                F.lit(1).alias(c2) if i1 == i2 else F.lit(0).alias(c2) 
                for i2, c2 in enumerate(columns)
            ])
        ) 
        for i1, c1 in enumerate(columns)
    ]).alias('cat')
).selectExpr(
    'id', 
    'inline(filter(cat, x -> x is not null))'
)

df2.show()
+---+-----+-----+-----+
| id|cat_1|cat_2|cat_3|
+---+-----+-----+-----+
|  1|    1|    0|    0|
|  1|    0|    1|    0|
+---+-----+-----+-----+

相关问题