【问题标题】:spark convert dataframe to dataset using case class with option fields火花使用带有选项字段的案例类将数据框转换为数据集
【发布时间】:2019-08-02 11:54:39
【问题描述】:

我有以下案例类:

case class Person(name: String, lastname: Option[String] = None, age: BigInt) {}

还有下面的json:

{ "name": "bemjamin", "age" : 1 }

当我尝试将我的数据框转换为数据集时:

spark.read.json("example.json")
  .as[Person].show()

它显示以下错误:

线程“主”org.apache.spark.sql.AnalysisException 中的异常: 给定输入列无法解析“lastname”:[年龄,姓名];

我的问题是:如果我的架构是我的案例类,并且它定义姓氏是可选的,那么 as() 不应该进行转换吗?

我可以使用 .map 轻松解决此问题,但我想知道是否有其他更清洁的替代方法。

【问题讨论】:

  • 嗨,如果您在其中添加另一个带有姓氏的 json(记录 2),如果它有效,那么我认为它会将架构推断为三列。以您只有一条记录的示例,spark(或任何人)如何知道您打算拥有 3 列?

标签: scala apache-spark apache-spark-sql apache-spark-dataset


【解决方案1】:

我们还有一个选项来解决上述问题。需要 2 个步骤

  1. 确保将可能缺失的字段声明为可为空 Scala 类型(如 Option[_])。

  2. 提供一个架构参数,而不依赖于架构推断。您可以使用例如 Spark SQL 编码器

    import org.apache.spark.sql.Encoders
    
    val schema = Encoders.product[Person].schema
    

您可以如下更新代码。

val schema = Encoders.product[Person].schema

val df = spark.read
           .schema(schema)
           .json("/Users/../Desktop/example.json")
           .as[Person]

+--------+--------+---+
|    name|lastname|age|
+--------+--------+---+
|bemjamin|    null|  1|
+--------+--------+---+

【讨论】:

    【解决方案2】:

    当你在执行spark.read.json("example.json").as[Person].show()时,它基本上是把数据帧读取为,

    FileScan json [age#6L,name#7]
    

    然后尝试为 Person 对象应用编码器,从而得到 AnalysisException,因为它无法从您的 json 文件中找到 lastname

    您可以通过提供一些具有姓氏的数据来暗示 spark 姓氏是可选的,或者 试试这个:

    val schema: StructType = ScalaReflection.schemaFor[Person].dataType.asInstanceOf[StructType]
    val x = spark.read
          .schema(schema)
          .json("src/main/resources/json/x.json")
          .as[Person]
    +--------+--------+---+
    |    name|lastname|age|
    +--------+--------+---+
    |bemjamin|    null|  1|
    +--------+--------+---+
    

    希望对你有帮助。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-01-03
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多