今天学习一下 Spark 的数据结构,分别是:
- RDD:弹性分布式数据集;
- 累加器:分布式共享只写变量;
- 广播变量:分布式共享只读变量。
它们分别用于不同的场景解决不同的问题。
1.RDD
RDD(Resilient Distributed Dataset) 弹性分布式数据集,是 Spark 最基本的数据处理模型,它是代码中的抽象类。对弹性分布式数据集的解释如下:
- 弹性:
- 存储的弹性:内存与磁盘自动切换;
- 容错的弹性:数据丢失可以自动恢复;
- 计算的弹性:计算出错重试;
- 分片的弹性:根据需要重新分片。
- 分布式:数据存储在不同节点上。
- 数据集:封装的是计算逻辑,不保存数据。
RDD 是代码中的抽象类,需要子类实现。RDD 不可变,想要改变只能产生新的 RDD 重新封装计算逻辑。RDD 可分区,里面的元素可以并行计算。
1.1 五大核心属性
- 分区列表:数据集的基本组成单位,标记数据是哪个分区的,执行任务时并行计算;
- 分区计算函数:Spark 在计算时,是使用分区函数对每一个分区进行计算;
- RDD 之间的依赖关系:需要将多个计算模型进行组合时,就需要将多个 RDD 建立依赖关系;
- 分区器 Partitioner:当数据为 key-value 类型数据时,可以通过设定分区器自定义数据的分区;
- 首选位置:移动数据不如移动计算,根据计算节点的状态选择不同的节点位置进行计算;
1.2 执行原理
申请资源→分解计算任务→发送到计算节点→计算→结果。RDD 在整个流程中主要用于将逻辑进行封装,并生成 Task 发送给 Executor 节点执行计算
在 Yarn 模式下,具体如下:
- Spark 通过申请资源创建调度节点和计算节点
- 一个 NodeManager 运行 Driver
- 其余 NodeManager 运行 Executor
- Driver 根据需求将计算逻辑根据分区划分不同的任务(Task)
- 调度节点(Driver)将任务(Task)发送到计算节点
- 计算节点(Executor)执行计算
2.累加器
累加器用来把 Executor 端变量信息聚合到 Driver 端。在 Driver 程序中定义的变量,在 Executor 端的每个 Task 都会得到这个变量的一份新的副本,每个 Task 更新这些副本的值后,传回 Driver 端进行 merge。
3.广播变量
Task 执行的算子中使用了外部的变量,每个 Task 都会获取一份变量的副本,造成大量的序列化反序列化开销和网络 IO。如果使用广播变量,向所有 Executor 发送一个较大的只读值,以供一个或多个 Task 操作使用,这样的话就可以让变量产生的副本大大减少,从而减少传输过程中的IO。比如,如果你的应用需要向所有节点发送一个较大的只读查询表,此时可以使用广播变量。在多个并行操作中使用同一个变量,但是 Spark 会为每个任务分别发送。
欢迎关注。