Spark持久化

1 血缘,缓存,rdd机制

rdd算子本身记录的是元数据,比如某个数据在某个区。他自己不存储数据本身。

(只存储分区和计算方法的数据)

所以 血缘关系(运算流程)或者RDD可以重用 但是数据不可重用

这意味着每次调用都需要 重新运算

这也是为什么 缓存或者持久化可以提升运行10倍运行速度的原因

因为之前数据虽然在内存里计算,但是并没有存储下来。持久化和缓存才是记录了数据。

rdd1=map(sss)
rdd2=rdd1.reducebykey

rdd1实际没有保存数据,只记录了血缘。所以当rdd2调用rdd1时。rdd1得重头计算一次。

2 RDD中cache,persist,checkpoint的区别

cache

数据会被缓存到内存来复用

血缘关系中添加新依赖

作业执行完毕时,数据会丢失

persist

保存在内存或磁盘

因为有磁盘IO,所以性能低,但是数据安全

作业执行完毕,数据会丢失

checkpoint

数据可以长时间保存到磁盘中

涉及磁盘IO,读取慢但安全。

独立作业

与cache配合使用,比如checkpoint后再cache一下,这样后续调用可以从cache里取

会切断血缘信息,重新建立新的血缘

checkpoint相当于改变数据源

3 Tips

触发方式:并不是立即缓存,当有action被触发时才调用。

object StorageLevel {
  //不缓存
  val NONE = new StorageLevel(false, false, false, false)
  //只在硬盘缓存
  val DISK_ONLY = new StorageLevel(true, false, false, false)
  //在硬盘缓存两份
  val DISK_ONLY_2 = new StorageLevel(true, false, false, false, 2)
  //只在内存缓存
  val MEMORY_ONLY = new StorageLevel(false, true, false, true)
  //在内存缓存两份
  val MEMORY_ONLY_2 = new StorageLevel(false, true, false, true, 2)
  //在内存序列化缓存
  val MEMORY_ONLY_SER = new StorageLevel(false, true, false, false)
  //在内存序列化缓存两份
  val MEMORY_ONLY_SER_2 = new StorageLevel(false, true, false, false, 2)
  //同时在内存和硬盘缓存
  val MEMORY_AND_DISK = new StorageLevel(true, true, false, true)
  //同时在内存和硬盘缓存两份(推荐)
  val MEMORY_AND_DISK_2 = new StorageLevel(true, true, false, true, 2)
  //同时在内存和硬盘序列化缓存
  val MEMORY_AND_DISK_SER = new StorageLevel(true, true, false, false)
  //同时在内存和硬盘序列化缓存两份
  val MEMORY_AND_DISK_SER_2 = new StorageLevel(true, true, false, false, 2)
  //对外内存
  val OFF_HEAP = new StorageLevel(false, false, true, false)
  ......
}

上面所有的存储级别,下面时构造器

class StorageLevel private(
    private var _useDisk: Boolean,
    private var _useMemory: Boolean,
    private var _useOffHeap: Boolean,
    private var _deserialized: Boolean,
    private var _replication: Int = 1)
  extends Externalizable {
  ......
  def useDisk: Boolean = _useDisk
  def useMemory: Boolean = _useMemory
  def useOffHeap: Boolean = _useOffHeap
  def deserialized: Boolean = _deserialized
  def replication: Int = _replication
  ......
}

offheap就是jvm的堆内存以外的内存。操作系统管理的内存,降低GC压力。

deserialized时反序列化,按java的方式加载数据。

副本数是在多少个节点上备份。

cache方法其实也是调用persist,只不过参数是memort_only

persist默认参数是disk_only