如何将空数组转换为null?

Ali*_*ice 3 apache-spark apache-spark-sql pyspark pyspark-sql

我有下面的数据框,我需要将空数组转换为null。

+----+---------+-----------+
|  id|count(AS)|count(asdr)|
+----+---------+-----------+
|1110| [12, 45]|   [50, 55]|     
|1111|       []|         []|    
|1112| [45, 46]|   [50, 50]|   
|1113|       []|         []|
+----+---------+-----------+
Run Code Online (Sandbox Code Playgroud)

我试过下面的代码不起作用。

df.na.fill("null").show()
Run Code Online (Sandbox Code Playgroud)

预期输出应为

+----+---------+-----------+
|  id|count(AS)|count(asdr)|
+----+---------+-----------+
|1110| [12, 45]|   [50, 55]|     
|1111|     NUll|       NUll|    
|1112| [45, 46]|   [50, 50]|   
|1113|     NUll|       NUll|
+----+---------+-----------+
Run Code Online (Sandbox Code Playgroud)

Ram*_*jan 7

对于给定的dataframe,您可以简单地执行以下操作

from pyspark.sql import functions as F
df.withColumn("count(AS)", F.when((F.size(F.col("count(AS)")) == 0), F.lit(None)).otherwise(F.col("count(AS)"))) \
    .withColumn("count(asdr)", F.when((F.size(F.col("count(asdr)")) == 0), F.lit(None)).otherwise(F.col("count(asdr)"))).show()
Run Code Online (Sandbox Code Playgroud)

您应该将输出dataframe

+----+---------+-----------+
|  id|count(AS)|count(asdr)|
+----+---------+-----------+
|1110| [12, 45]|   [50, 55]|
|1111|     null|       null|
|1112| [45, 46]|   [50, 50]|
|1113|     null|       null|
+----+---------+-----------+
Run Code Online (Sandbox Code Playgroud)

更新

如果您有两个以上的数组列,并且要动态应用上述逻辑,则可以使用以下逻辑

from pyspark.sql import functions as F
for c in df.dtypes:
    if "array" in c[1]:
        df = df.withColumn(c[0], F.when((F.size(F.col(c[0])) == 0), F.lit(None)).otherwise(F.col(c[0])))
df.show()
Run Code Online (Sandbox Code Playgroud)

在这里,
df.dtypes将为您提供具有列名和数据类型的元组数组。至于问题中的数据框

[('id', 'bigint'), ('count(AS)', 'array<bigint>'), ('count(asdr)', 'array<bigint>')]
Run Code Online (Sandbox Code Playgroud)

withColumn仅适用于数组("array" in c[1]),其中F.size(F.col(c[0])) == 0条件检查when函数用于检查数组的大小。如果条件为true,即为空数组,则填充None,否则填充原始值。该循环将应用于所有数组列。