Чтение CSV-файлов с отсутствующими столбцами и случайным порядком столбцов

У меня есть схема, которую я хочу применить к CSV-файлам в Databricks. Файлы csv могут содержать 6 столбцов (a,b,c,d,e,f), которые могут появляться в файлах csv в случайном порядке. Также может случиться так, что один или несколько столбцов отсутствуют. Таким образом, файлы csv с этими заголовками будут действительными.

a,b,c,d,e,f
f,e,d,c,a,b
a,b,c
d,e,f

Я могу создать пользовательскую схему, но она не обрабатывает другой порядок, а также отсутствующие столбцы. Они применяются последовательно. Любые идеи о том, как с этим можно справиться?

customSchema = StructType() \
  .add("a", DoubleType(), True) \
  .add("b", DoubleType(), True) \
  .add("c", DoubleType(), True) \
  .add("d", DoubleType(), True) \
  .add("e", DoubleType(), True) \
  .add("f", DoubleType(), False)


data = sqlContext.read.format("csv") \
  .option("header", "true") \
  .option("delimiter", ",") \
  .schema(customSchema) \
  .load("*.csv")

person reachify    schedule 04.07.2018    source источник
comment
Какое поведение вы ожидаете для отсутствующих столбцов?   -  person Oli    schedule 04.07.2018


Ответы (1)


Вы можете прочитать CSV-файл без указания схемы, а затем сформировать фрейм данных так, как вам нравится. В scala это будет выглядеть так:

val df = spark.read.format("csv")
    .option("header", "true")
    .load("x.csv")

val cols = Seq("a", "b", "c", "d", "e", "f")

/* Here I select and cast the column if it exists. 
   I create a null column otherwise */
val shaped_df = df.select( cols.map(c=> 
    if(df.columns.contains(c)) 
        col(c).cast("double") 
    else 
        lit(null).cast("double").alias(c)
) :_* )

shaped_df.printSchema()
root
    |-- a: double (nullable = true)
    |-- b: double (nullable = true)
    |-- c: double (nullable = true)
    |-- d: double (nullable = true)
    |-- e: double (nullable = true)
    |-- f: double (nullable = true)
person Oli    schedule 04.07.2018