【问题标题】:How to read csv file with additional comma in quotes using pyspark?如何使用pyspark读取带有额外逗号的csv文件?
【发布时间】:2021-02-08 01:15:32
【问题描述】:

我在读取UTF-16 中的以下 CSV 数据时遇到了一些问题:

FullName, FullLabel, Type
TEST.slice, "Consideration":"Verde (Spar Verde, Fonte Verde)", Test,

据我了解,这对读者来说应该不是问题,因为有一个quote 参数来处理它。

df = spark.read.csv(file_path, header=True, encoding='UTF-16', quote = '"')

但是,这仍然会给我一个不正确的拆分:

有什么方法可以处理这些情况,还是我需要使用 RDD 来解决?

提前谢谢你。

【问题讨论】:

  • 尝试像这样引用:quote = '\"'。那是使用转义字符。让我们知道这是否有效。
  • 引号应该包含整个列,而不是列的一部分
  • @vijayinani 不幸的是:/
  • 这里需要一些正则表达式。一些正则表达式专家可以提供帮助。

标签: python apache-spark pyspark apache-spark-sql pyspark-dataframes


【解决方案1】:

您可以使用spark.read.text 将值读取为文本,并使用一些正则表达式将值拆分为逗号,但忽略引号(您可以看到此post),然后从结果数组中获取相应的列:

from pyspark.sql import functions as F

df = spark.read.text(file_path)

df = df.filter("value != 'FullName, FullLabel, Type'") \
    .withColumn(
    "value",
    F.split(F.col("value"), ',(?=(?:[^\"]*\"[^\"]*\")*[^\"]*$)')
).select(
    F.col("value")[0].alias("FullName"),
    F.col("value")[1].alias("FullLabel"),
    F.col("value")[2].alias("Type")
)

df.show(truncate=False)

#+----------+--------------------------------------------------+-----+
#|FullName  |FullLabel                                         |Type |
#+----------+--------------------------------------------------+-----+
#|TEST.slice| "Consideration":"Verde (Spar Verde, Fonte Verde)"| Test|
#+----------+--------------------------------------------------+-----+

更新:

对于utf-16中的输入文件,您可以通过将文件加载为binaryFiles来替换spark.read.text,然后将生成的rdd转换为数据框:

df = sc.binaryFiles(file_path) \
    .flatMap(lambda x: [[l] for l in x[1].decode("utf-16").split("\n")]) \
    .toDF(["value"])

【讨论】:

    【解决方案2】:

    下面的另一个选项(如果你觉得简单的话):

    首先将文本文件读取为RDD,并将":"替换为~:~并保存文本文件。

    sc.textFile(file_path).map(lambda x: x.replace('":"','~:~')).saveAsTextFile(tempPath)
    

    接下来,读取临时路径并再次将 ~:~ 替换为 ":",但这次是作为 DF。

    from pyspark.sql import functions as F
    spark.read.option('header','true').csv(tempPath).withColumn('FullLabel',F.regexp_replace(F.col('FullLabel'),'~:~','":"')).show(1, False)
    
    +----------+-----------------------------------------------+----+
    |FullName  |FullLabel                                      |Type|
    +----------+-----------------------------------------------+----+
    |TEST.slice|Consideration":"Verde (Spar Verde, Fonte Verde)|Test|
    +----------+-----------------------------------------------+----+
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2019-03-13
      • 2020-09-07
      • 2015-12-21
      • 2019-03-28
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多