(1) persist算子
- 使用方法:
var rdd = sc.textFile("test")
rdd = rdd.persist(StorageLevel.MEMORY_ONLY)
val count = rdd.count() //或者其他操作
- StorageLevel說明:
StorageLevel的構(gòu)造函數(shù):
class StorageLevel private(
private var _useDisk: Boolean, # 是否存入磁盤
private var _useMemory: Boolean, # 是否存入內(nèi)存
private var _useOffHeap: Boolean, # 是否使用堆外內(nèi)存
private var _deserialized: Boolean, # 是否不進(jìn)行序列化
private var _replication: Int = 1 # 副本數(shù)(默認(rèn)為1))
StorageLevel object中已經(jīng)定義了幾種代表RDD持久化的級別:
image.png
使用不同參數(shù)的組合構(gòu)造的實(shí)例被預(yù)先定義為一些值蛔屹,比如MEMORY_ONLY代表著不存入磁盤娄蔼,存入內(nèi)存譬圣,不使用堆外內(nèi)存,不進(jìn)行序列化课幕,副本數(shù)為1,使用persisit()方法時(shí)把這些持久化的級別作為參數(shù)傳入即可。
(2) cache算子
cache() = persist(StorageLevel.MEMORY_ONLY)
(3) checkpoint算子:可以把RDD持久化到HDFS
使用方法:
使用方法:
sc.setCheckpointDir("hdfs://...")
var rdd = sc.textFile("test")
rdd.checkpoint()
val count = rdd.count() //或者其他操作
checkpoint()執(zhí)行原理:
- 當(dāng)RDD的job執(zhí)行完畢后数焊,會從finalRDD從后往前回溯
- 當(dāng)回溯到調(diào)用了checkpoint()方法的RDD后,會給這個(gè)RDD做一個(gè)標(biāo)記
- Spark框架自動啟動一個(gè)新的job崎场,計(jì)算這個(gè)RDD的數(shù)據(jù)佩耳,然后把數(shù)據(jù)持久化到HDFS上
- 優(yōu)化:對某個(gè)RDD執(zhí)行checkpoint()之前,對該RDD執(zhí)行cache()照雁,這樣的話蚕愤,新啟動的job只需要把內(nèi)存中的數(shù)據(jù)上傳到HDFS中即可,不需要重新計(jì)算饺蚊。
(4) 關(guān)于這3個(gè)算子的幾點(diǎn)說明
- 這3個(gè)算子都是Transformations類算子萍诱,需要Actions類算子觸發(fā)才能執(zhí)行
- cache 和 persist 算子的返回執(zhí)行必須賦值給一個(gè)變量,在接下來的job中直接使用這個(gè)變量污呼,那么就是使用了持久化的數(shù)據(jù)了裕坊,如果application中只有一個(gè)job,沒有必要使用RDD持久化
- cache 和 persist 算子后不能立即緊跟action類算子燕酷,比如count算子籍凝,但是在下一行可以有action類算子
error :
cache().count()
right :
rdd = rdd.cache()
rdd.count()
- checkpoint()算子執(zhí)行后就切斷了RDD之間的依賴
當(dāng)業(yè)務(wù)邏輯很復(fù)雜時(shí),RDD之間頻繁轉(zhuǎn)換苗缩,RDD的血統(tǒng)很長饵蒂,如果中間某個(gè)RDD的數(shù)據(jù)丟失,還需要重新從頭計(jì)算酱讶,如果對中間某個(gè)RDD調(diào)用了checkpoint()方法退盯,把這個(gè)RDD上傳到HDFS,同時(shí)讓后面的RDD不再依賴于這個(gè)RDD泻肯,而是依賴于HDFS上的數(shù)據(jù)渊迁,那么下次計(jì)算會方便很多。 - checkpoint持久化到磁盤和persist持久化到磁盤的區(qū)別
- persist()把RDD持久化到磁盤灶挟,這個(gè)RDD的持久化數(shù)據(jù)保存在Worker的工作目錄下琉朽,且當(dāng)整個(gè)application執(zhí)行結(jié)束后,就會自動刪除持久化的數(shù)據(jù)
- checkpoint()持久化到指定的目錄稚铣,可以是HDFS箱叁,而且永久保存