1. 程式人生 > >spark RDD系列------2.HadoopRDD分割槽的建立以及計算

spark RDD系列------2.HadoopRDD分割槽的建立以及計算

     Spark經常需要從hdfs讀取檔案生成RDD,然後進行計算分析。這種從hdfs讀取檔案生成的RDD就是HadoopRDD。那麼HadoopRDD的分割槽是怎麼計算出來的?如果從hdfs讀取的檔案非常大,如何高效的從hdfs載入檔案生成HadoopRDD呢?本篇文章探討這兩個問題。

    SparkContext.objectFile方法經常用於從hdfs載入檔案,從載入hdfs檔案到生成HadoopRDD的函式呼叫過程為:

SparkContext.objectFile->

SparkContext.sequenceFile->

SparkContext.hadoopFile->

new HadoopRDD

SparkContext.objectFile方法定義如下:

def objectFile[T: ClassTag](
      path: String,
      minPartitions: Int = defaultMinPartitions): RDD[T] = withScope {
    assertNotStopped()
    sequenceFile(path, classOf[NullWritable], classOf[BytesWritable], minPartitions)
      .flatMap(x => Utils.deserialize[Array[T]](x._2.getBytes, Utils.getContextOrSparkClassLoader))
  }
def defaultMinPartitions: Int = math.min(defaultParallelism, 2)
從以上程式碼可知如果不設定載入的hdfs檔案生成的HadoopRDD的分割槽個數,預設最小分割槽個數是2

SparkContext.objectFile方法的minPartitions引數沒有改變,一直傳遞到HadoopRDD的建構函式

HadoopRDD.getPartitions方法用於建立HadoopRDD的分割槽。

在本篇文章中,以如下語句載入hdfs檔案建立HadoopRDD,建立的HadoopRDD分割槽個數最小是24個

val login1RDD = sc.objectFile[String]("/data/login/1448419800022", 24)
hdfs uri為:hdfs://ddos12/

hdfs上/data/login/1448419800022/目錄內的檔案情況,如下圖所示:


目錄下存在12個檔案,12個檔案總共10974245位元組,如果按照24個分割槽計算,平均一個分割槽是457260位元組

分割槽的 建立在HadoopRDD.getPartitions方法:

override def getPartitions: Array[Partition] = {
    val jobConf = getJobConf()
    // add the credentials here as this can be called before SparkContext initialized
    SparkHadoopUtil.get.addCredentials(jobConf)
    val inputFormat = getInputFormat(jobConf)
    if (inputFormat.isInstanceOf[Configurable]) {
      inputFormat.asInstanceOf[Configurable].setConf(jobConf)
    }
    /*
    * 確定當前目錄下有多少個分割槽,分割槽個數最小是minPartitions,以及每個分割槽多大,每個分割槽的資料所在的檔案,分割槽資料在檔案中的起始位置
    * */
    val inputSplits = inputFormat.getSplits(jobConf, minPartitions)
    val array = new Array[Partition](inputSplits.size)
    for (i <- 0 until inputSplits.size) {
      /*建立分割槽*/
      array(i) = new HadoopPartition(id, i, inputSplits(i))
    }
    array
  }
根據上面的檔案,建立的分割槽大概資訊如下:



可見總共建立了25個分割槽,通過上圖可得出結論在切分hdfs目錄中的檔案的時候,對每個檔案按照分割槽平均長度457260進行切分,每個分割槽的長度不能大於457260.比如說part-00009檔案,切分成了3個分割槽,最後一個分割槽的長度只有62107位元組

下圖表示了一個index為1分割槽的詳細資訊:


可見裡面包含了分割槽所在的hdfs的檔案,以及分割槽資料在這個檔案的起始位置,分割槽的大小

但是預設情況下,HadoopRDD一個分割槽最大是128M,假設一個檔案大小是1G+10M,但是我設定4個分割槽,那麼在計算分割槽個數的時候會計算為9個分割槽,最後一個分割槽大小為10M。