gpt4 book ai didi

apache-spark - Spark DataFrame 是无类型的 vs DataFrame 有架构?

转载 作者:行者123 更新时间:2023-12-03 22:13:55 25 4
gpt4 key购买 nike

我是 Spark 的初学者,在阅读 Dataframe 时,我经常发现以下两个关于 dataframe 的语句-

1) DataFrame 是无类型的
2) DataFrame 具有模式(如数据库表,其中包含与表属性相关的所有信息 - 名称、类型、非空)

这两个陈述不是相互矛盾的吗?首先,我们说 Dataframe 未键入,同时我们还说 Dataframe 具有有关所有列的信息,即架构,请帮助我在这里缺少什么?因为如果数据框有架构,那么它也知道列的类型,所以它是如何变成无类型的?

最佳答案

DataFrames 是动态类型的,而 Datasets 和 RDDs 是静态类型的。这意味着当您定义数据集或 RDD 时,您需要显式指定表示内容的类。这很有用,因为当您在数据集上编写转换时,编译器可以检查您的代码的类型安全性。以这个宠物信息数据集为例。当我使用 pet.speciespet.name 时,编译器在编译时就知道它们的类型。

case class Pet(name: String, species: String, age: Int, weight: Double)

val data: Dataset[Pet] = Seq(
Pet("spot", "dog", 2, 50.5),
Pet("mittens", "cat", 11, 15.5),
Pet("mickey", "mouse", 1, 1.5)).toDS
println(data.map(x => x.getClass.getSimpleName).first)
// Pet

val newDataset: Dataset[String] = data.map(pet => s"I have a ${pet.species} named ${pet.name}.")

当我们切换到使用 DataFrame 时,模式保持不变,数据仍然是类型化的(或结构化的),但这些信息仅在运行时可用。这称为动态类型。这可以防止编译器捕获您的错误,但它非常有用,因为它允许您编写类似 sql 的语句并动态定义新列,例如将列附加到现有的 DataFrame,而无需为每个定义一个新类小操作。另一方面是您可以定义导致空值或在某些情况下导致运行时错误的错误操作。
val df: DataFrame = data.toDF
df.printSchema()
// root
// |-- name: string (nullable = true)
// |-- species: string (nullable = true)
// |-- age: integer (nullable = false)
// |-- weight: double (nullable = false)

val newDf: DataFrame = df
.withColumn("some column", ($"age" + $"weight"))
.withColumn("bad column", ($"name" + $"age"))
newDf.show()
// +-------+-------+---+------+-----------+----------+
// | name|species|age|weight|some column|bad column|
// +-------+-------+---+------+-----------+----------+
// | spot| dog| 2| 50.5| 52.5| null|
// |mittens| cat| 11| 15.5| 26.5| null|
// | mickey| mouse| 1| 1.5| 2.5| null|
// +-------+-------+---+------+-----------+----------+

关于apache-spark - Spark DataFrame 是无类型的 vs DataFrame 有架构?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52288412/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com