Scala 动态和可配置地更改多个Spark DataFrame列类型

Scala 动态和可配置地更改多个Spark DataFrame列类型,scala,apache-spark-sql,Scala,Apache Spark Sql,我对Spark和Scala不熟悉 我们有一个外部数据源为我们提供JSON。此JSON在所有值(包括数字和布尔字段)周围都有引号。所以当我把它放到我的数据框中时,所有的列都是字符串。最终目标是将这些JSON记录转换为正确类型的拼花文件 大约有100个字段,我需要将其中一些类型从string更改为int、boolean或bigint(long)。此外,我们处理的每个数据帧将只有这些字段的一个子集,而不是所有字段。因此,我需要能够处理给定数据帧的列子集,将每个列与已知的列类型列表进行比较,并根据数据帧

我对Spark和Scala不熟悉

我们有一个外部数据源为我们提供JSON。此JSON在所有值(包括数字和布尔字段)周围都有引号。所以当我把它放到我的数据框中时,所有的列都是字符串。最终目标是将这些JSON记录转换为正确类型的拼花文件

大约有100个字段,我需要将其中一些类型从string更改为int、boolean或bigint(long)。此外,我们处理的每个数据帧将只有这些字段的一个子集,而不是所有字段。因此,我需要能够处理给定数据帧的列子集,将每个列与已知的列类型列表进行比较,并根据数据帧中出现的列将某些列从string转换为int、bigint和boolean

最后,我需要可以配置的列类型列表,因为我们将来会有新的列,并且可能希望删除或更改旧的列

到目前为止,我的情况如下:

// first I convert to all lower case for column names
val df = dfIn.toDF(dfIn.columns map(_.toLowerCase): _*)

// Big mapping to change types
// TODO how would I make this configurable?
// I'd like to drive this list from an external config file.
val dfOut = df.select(
   df.columns.map {

     ///// Boolean
     case a @ "a" => df(a).cast(BooleanType).as(a)
     case b @ "b" => df(b).cast(BooleanType).as(b)

     ///// Integer
     case i @ "i" => df(i).cast(IntegerType).as(i)
     case j @ "j" => df(j).cast(IntegerType).as(j)


     // Bigint to Double
     case x @ "x" => df(x).cast(DoubleType).as(x)
     case y @ "y" => df(y).cast(DoubleType).as(y)

     case other         => df(other)
   }: _*
)
这是将这些数据转换为Scala中所需类型的有效方法吗


我可以从一个外部“配置”文件中得到一些建议,在这个文件中我可以定义列类型。

我的问题演变成了这个问题。答案很好: