什么是Spark
Spark 是一个开源的分布式查询和处理引擎。
提供MapReduce的灵活性和扩展性:
- 当数据存储在内存时比Apache Hadoop快100倍
- 访问磁盘时高达10倍
允许用户读取、转换、聚合数据,还可以训练部署复杂的统计模型。
Java、Scala、Python、R、SQL都可以访问Spark API。
Spark 提供了几个已经实现并调优过的算法、统计模型和框架:
- 机器学习-MLlib和ML
- 图形处理-GraphX、GraphFrames
- 流计算-Spark Streaming (DStream和Structured)
允许用户在同一个应用程序中随意地组合使用这些库。
可以从不同的数据源读取和写入,包括但不限于 HDFS、Cassandra、HBase和S3。
作业和API
执行过程
任何Spark应用程序都会分离主节点上的单个驱动进程
(可以包含多个作业),然后将执行进程
(包含多个任务)分配给多个工作节点。
驱动进程
会确定任务进程
的数量和组成,这些任务进程
是根据为指定作业生成的图形分配给执行节点
的。任何工作节点都可以执行来自多个不同作业的多个任务。
Spark作业与一系列对象依赖相关联,这些依赖关系是以有向无环图
(DAG)的方式组织的。基于这些,Spark可以优化调度
(例如确定所需的任务和工作节点的数量)并执行这些任务。
弹性分布式数据集RDD
弹性分布式数据集(简称RDD)是不可变Java虚拟机(JVM)对象的分布式集合,Spark就是围绕着RDD而构建的。我们使用Python时,Python数据是存储在这些JVM对象中的。
这些对象允许作业非常快速地执行计算。对RDD的计算依据缓存
和存储在内存
中的模式进行:与其他传统分布式框架(如Apache Hadoop)相比,该模式使得计算速度快了一个数量级。
同时,RDD会给出一些粗粒度的数据转换(例如map
(…)、reduce
(…)和filter
(…)),保持Hadoop平台的灵活性和可扩展性,以执行各种各样的计算。
RDD以并行
方式应用和记录数据转换,从而提高了速度和容错能力。通过注册这些转换,RDD提供数据沿袭——以图形
形式给出的每个中间步骤
的祖先树
。这实际上保护RDD免于数据丢失——如果一个RDD的分区丢失,它仍然具有足够的信息来重新创建该分区,而不是简单地依赖复制。
RDD有两组并行操作:
- 转换(返回指向新RDD的指针)
- 动作(在运行计算后向驱动程序返回值)
某种意义上来说,RDD转换操作是惰性的,因为它们不立即计算其结果。只有动作执行了并且需要将结果返回给驱动程序时,才会计算转换。
该延迟执行会产生更多精细查询:针对性能进行优化的查询。
- 这种优化始于Spark的DAG Scheduler——面向阶段的调度器,使用如上面截图中所示的阶段进行转换。由于具有单独的RDD转换和动作,DAG Scheduler可以在查询中执行优化,包括能够避免shuffle数据(最耗费资源的任务)。
DataFrame
Data Frame像RDD一样,是分布在集群的节点中的不可变
的数据集合
。然而,与RDD不同的是,在DataFrame中,数据是以命名列
的方式组织的。
DataFrame的一个主要优点是,Spark引擎一开始就构建了一个逻辑执行计划,而且执行生成的代码是基于成本优化程序确定的物理计划。与Java或者Scala相比,Python中的RDD是非常慢的,而DataFrame的引入则使性能在各种语言中都保持稳定。
Dataset
Spark 1.6中引入的Dataset旨在提供一个API,允许用户轻松地表达域对象的转换,同时还提供了具有强大性能和优点的Spark SQL执行引擎。但目前Dataset仅在Scala或Java中可用。
Catalyst 优化器
Spark SQL是Spark最具技术性的组件之一,因为它支持SQL查询和DataFrameAPI。
Spark SQL的核心是Catalyst优化器。优化器基于函数式
编程结构,并且旨在实现两个目的:简化向Spark SQL添加新的优化技术和特性的条件,并允许外部开发人员扩展优化器(例如,添加数据源特定规则,支持新的数据类型等等)
Spark 2.0的架构
Spark2.0的引入是ApacheSpark项目基于过去两年平台开发经验近期所发布的主要版本更新,发布三个重要主题包括性能增强:
- 通过TungstenPhase2
- 引入结构化
流
- 统一Dataset和DataFrame
统一Dataset和DataFrame
Dataset于2015年作为Spark1.6版本的一部分推出。
Dataset的目标是提供一个类型安全的编程接口。这允许开发人员使用编译时类型安全(生产应用程序可以在运行之前检查错误)处理半结构化数据(如JSON或键值对)。Python不实现DatasetAPI的部分原因是Python不是一种类型安全的语言。
Dataset API包含高级别域的特定语言操作,如sum
()、avg
()、join
()和group
()。这种最新的特性意味着不仅具有传统Spark RDD的灵活性,而且代码也更容易表达、读取和写入。
与DataFrame类似,Dataset可以通过将表达式和数据字段暴露给查询计划器并借助Tungsten的快速内存编码来运用Spark的Catalyst优化器。
现在DataFrame和Dataset都属于新的DatasetAPI,作为ApacheSpark2.0的一部分被引入进来DataFrame和Dataset已统一为Apache Spark2.0的一部分,DataFrame是未类型化的DatasetAPI的一个别名。
类比来说:
DataFrame = Dataset[Row]
SparkSession 介绍
在过去,可能会使用SparkConf、SparkContext、SQLContext和HiveContext来分别执行配置、Spark环境、SQL环境和Hive环境的各种Spark查询。SparkSession本质上是这些环境的组合,包括StreamingContext。它是读取数据、处理元数据、配置会话和管理集群资源的入口。
Tungsten Phase 2
Project Tungsten于2015年推出,旨在为Spark引擎的性能提高做出显著改进。这些改进的第一阶段侧重于以下几个方面:
- 内存管理和二进制处理
- 高速缓存感知计算
- 代码生成
- 没有虚拟函数调度
- CPU寄存器存储中间数据
- 循环展开和SIMD
结构化流
基础。虽然流媒体功能强大,但关键问题之一是流可能难以构建和维护。为了简化SparkStreaming,现在有一个单一API可以解决Spark2.0版本中的批处理和流式处理。
更简洁地说,高级流API现在构建在SparkSQL引擎之上。它运行的查询与使用Dataset、DataFrame时完全相同,为你提供所有性能和优化以及事件时间、窗口、会话(session)、源(source)和槽(sink)等方面的优势。
连续应用
总而言之,Spark2.0不仅统一了DataFrame和Dataset,而且统一了流、交互式和批处理查询。产生了一整套新的用例,包括将数据聚合到流中并使用传统的JDBC/ODBC提供它,在运行时更改查询,或在多种场景中构建和应用ML模型的延迟用例。
同时,你可以构建端到端的连续应用程序,在其中可以对实时数据进行批处理
,执行ETL
、生成报告、更新或跟踪流中的特定数据。