我有一个空间交付的csv文件,其中包含如下键值对:-
a=1 b=";2021-02-21 00:00:12";c=5
我必须通过pyspark来阅读。
我使用了以下命令:-
a=spark.read.option(quote,quote(.option('delimiter',''(.csv(/path/abc.csv(
当我执行上面的操作时,它会创建4列而不是3列,如下所示:-
a=1|b=";2021-02-21|00:00:12"|c=5
有人能帮我怎么把b的全部值放在一列中吗。
注意:这只是一个样本记录。实际记录的多个k-v对以及列的顺序在我们收到的每个文件中都不相同。
您可以使用concat_ws
连接两列,使用df.columns[n]
通过索引访问列
from pyspark.sql.functions import concat_ws
df = df.select(concat_ws('',df.columns[1],df.columns[2]).alias("b"),"a","c")
由于不能使用正则表达式,因此要根据键值对分隔列,可以读取孔线,并将F.split
函数与一些F.pivot
魔术一起使用。
(spark.read.text("test.csv")
.withColumn("line_id", F.monotonically_increasing_id())
.withColumn("array", F.split("value",r"( )?[a-z]="))
.withColumn("keys", F.array([F.lit(x) for x in list("abc")]))
.select(F.col("line_id"),
F.arrays_zip(F.slice(F.col("keys"),1,3),
F.slice(F.col("array"),2,4)).alias("value"))
.select(F.col("line_id"),F.explode("value").alias("exploded"))
.select(F.col("line_id"),
F.col("exploded").getItem("0").alias("key"),
F.col("exploded").getItem("1").alias("val"))
.groupBy("line_id").pivot("key").agg(F.max("val"))
.show(10, False))
结果应该是:
+-------+---+---------------------+---+
|line_id|a |b |c |
+-------+---+---------------------+---+
|0 |1 |"2021-02-21 00:00:12"|5 |
|1 |3 |"2021-02-21 00:00:52"|4 |
+-------+---+---------------------+---+