Chapter 3. DataFrames, Datasets, and Spark SQL
Spark SQLand its DataFrames and Datasets
是Spark性能的未来,具有更高效的存储、
更
高级优化器和
更
直接
的
操作
序列化数据
。
这些组件是超级重要为获得最佳spark性能(见图3-1)。
这些都是相对较新的组成部分;
在Spark 1.6中介绍了Datasets
,在Spark 1.3中介绍了DataFrames,在Spark 1.0中介绍了SQL引擎。
这一章的重点是帮助您学习如何最好地使用Spark SQL的工具,以及如何将Spark sql与传统的Spark操作混合使用。
注:
Spark的DataFrames
与传统的DataFrames
(如Panda的和R的)相比,具有非常不同的功能。虽然这些都处理结构化数据,但重要的是不要依赖于您现有的对DataFrames
的直觉。
与RDDs一样,DataFrames
和Datasets
表示分布式集合,并带有RDDs中没有的额外模式信息。
这些额外的模式信息用于提供更高效的存储层(钨),并在优化器(Catalyst)中执行额外的优化。
除了模式信息之外,在DataFrames
和Datasets
上执行的操作使得优化器可以检查逻辑意义,而不是任意函数。
DataFrames是Datasets的
一个特殊的Row对象
,它在
编译时
不提供任何类型检查。
强类型Datasets
API特别适合用于更类似rdd的函数操作。
与使用RDDs相比,DataFrames允许Spark的优化器更好地理解我们的代码和数据,这允许我们在'查询优化器'中探索的一类新的优化
注;
虽然Spark SQL、DataFrames和Datasets
提供了许多优秀的增强,但与常规RDDs的传统处理相比,它们仍有一些粗糙之处。
Dataset API在撰写本文时还是全新的,将来的版本可能会有一些变化。
开始使用SparkSession(或HiveContext或SQLContext)
就像SparkContext是所有Spark应用程序的入口点,StreamingContext是所有流应用程序的入口点一样,SparkSession是SparkSQL的入口点。
与所有Spark组件一样,您需要导入一些额外的组件,如示例3-1所示。
提示:
如果您正在使用Spark Shell,您将自动获得一个名为Spark的SparkSession,以配合名为sc的SparkContext(没明白)
Scala类型的别名DataFrame = Dataset[Row]被打破在Java你必须使用Dataset<Row>
代替。
SparkSession通常使用生成器模式和getOrCreate()创建,后者将返回一个已经运行的会话。
构建器可以采用基于字符串的配置键
config(key, value)
,并且存在许多常用参数的快捷方式。
一个更重要的快捷方式是enableHiveSupport(),它将允许您访问Hive UDFs,并且不需要安装Hive,但是需要某些额外的jar(在Spark SQLDependencies中讨论)。
示例3-2展示了如何创建一个支持Hive的SparkSession。
enableHiveSupport()快捷方式不仅配置Spark SQL去使用这些Hive jar,而且还迫切地检查它们是否能够被加载,从而比手动设置配置值更清晰的错误消息。
通常情况下,
建议
使用API文档中列出的快捷方式,因为在通用配置界面中没有检查。
注:在使用getOrCreate时,如果现有的会话存在,您的配置值可能会被忽略,您将只获得现有的SparkSession。
有些选项,比如master,也只适用于没有运行SparkContext的情况;
否则,将使用现有的SparkContext
在Spark2.0之前,SparkSQL使用两个单独的入口点(HiveContext或SQLContext),而不是SparkSession。
这些入口点的名称可能有点令人困惑,但是需要注意的是HiveContext不需要安装Hive。
使用SQLContext的主要原因是无法解决的Hive依赖冲突。
与SQLContext相比,HiveContext有一个更完整的SQLparser,以及额外的用户定义函数(udf)。
例3-4展示了如何创建一个遗留的HiveContext。
如果可能,应该首选SparkSession,然后是HiveContext,然后是SQLContext。
并不是所有的库,甚至所有的Spark代码都被更新为使用SparkSession,在某些情况下,您会发现仍然需要SQLContext或HiveContext的函数。
如果您需要构造一个遗留接口(SQLContext或HiveContext),那么示例3-3中的额外导入将非常有用。
提示:
从SparkSession获取HiveContext或SQLContext在外部不受很好的支持
org.apache.spark scope
-但是,可以使用getOrCreate。
Spark SQL Dependencies
与Spark中的其他组件一样,使用Sparksql需要添加额外的依赖项。
如果您与Hive JAR之间存在无法通过
shading
解决的冲突,那么您可以将自己限制在spark-sql JAR上,尽管您希望访问Hive依赖项不包括spark-hive JAR。
要在SparkSession中启用Hive支持或使用HiveContext,您需要将Spark的SQL和Hive组件添加到您的依赖项中。
对于与maven兼容的构建系统,2.0.0中Spark的SQL和Hive组件的坐标是org.apache.spark: Spark -sql_2.11:2.0.0和org.apache.spark: Spark -hive_2.11:2.0.0。
示例3-5展示了如何将它们添加到常规的sbt构建中,示例3-6展示了针对Maven用户的过程。
Managing Spark Dependencies
虽然手工管理这些依赖关系并不是特别具有挑战性,但有时在更新版本时可能会出现错误。
e sbt-spark-package
插件可以简化对Spark依赖项的管理。
此插件通常用于创建社区包(在
“Creating a Spark Package”)
中讨论),但也帮助构建依赖于Spark的软件。
要将插件添加到sbt构建中,您需要创建一个项目/插件。
并确保它包含示例3-7中的代码。
要使Spark包工作,您需要指定Spark版本和至少一个Spark组件(核心),这可以在示例3-8所示的sbt设置中完成
安装并设置好sbst - Spark -package之后,您可以通过向sparkComponents列表中添加SQL和Hive来添加Spark组件,如示例3-9所示。
虽然这不是必需的,但如果您有一个现有的Hive Metastore,您希望与Spark连接,您可以复制Hive -site.xml到Spark的conf/目录。
提示:
默认的Hive Metastore版本是1.2.1。
对于其他版本的
Hive Metastore
,你需要设置
spark.sql.hive.metastore.version
属性,并设置spark.sql.hive.metastore.
jar到maven(让Spark检索jar)或Hive jar所在的系统路径。