zoukankan      html  css  js  c++  java
  • Hadoop基础(六十):面试题 Hadoop数据切片(二)切片机制源码

    来源:https://www.cnblogs.com/boccer/p/13735162.html

    切片机制源码:

    ①for (FileStatus file: files)   每个文件单独切片。

    ②long length = file.getLen()   获取文件大小。

    ③while (((double) bytesRemaining)/splitSize > SPLIT_SLOP)   SPLIT_SLOP值为1.1,如果一个文件大于切片大小,会被循环切成多片,如果切片后剩下的部分不足切片的1.1倍,则停止切片。

    复制代码
      /** 
       * Generate the list of files and make them into FileSplits.
       * @param job the job context
       * @throws IOException
       */
      public List<InputSplit> getSplits(JobContext job) throws IOException {
        StopWatch sw = new StopWatch().start();
        long minSize = Math.max(getFormatMinSplitSize(), getMinSplitSize(job));
        long maxSize = getMaxSplitSize(job);
    
        // generate splits
        List<InputSplit> splits = new ArrayList<InputSplit>();
        List<FileStatus> files = listStatus(job);
        for (FileStatus file: files) {
          Path path = file.getPath();
          long length = file.getLen();
          if (length != 0) {
            BlockLocation[] blkLocations;
            if (file instanceof LocatedFileStatus) {
              blkLocations = ((LocatedFileStatus) file).getBlockLocations();
            } else {
              FileSystem fs = path.getFileSystem(job.getConfiguration());
              blkLocations = fs.getFileBlockLocations(file, 0, length);
            }
            if (isSplitable(job, path)) {
              long blockSize = file.getBlockSize();
              long splitSize = computeSplitSize(blockSize, minSize, maxSize);
    
              long bytesRemaining = length;
              while (((double) bytesRemaining)/splitSize > SPLIT_SLOP) {
                int blkIndex = getBlockIndex(blkLocations, length-bytesRemaining);
                splits.add(makeSplit(path, length-bytesRemaining, splitSize,
                            blkLocations[blkIndex].getHosts(),
                            blkLocations[blkIndex].getCachedHosts()));
                bytesRemaining -= splitSize;
              }
    
              if (bytesRemaining != 0) {
                int blkIndex = getBlockIndex(blkLocations, length-bytesRemaining);
                splits.add(makeSplit(path, length-bytesRemaining, bytesRemaining,
                           blkLocations[blkIndex].getHosts(),
                           blkLocations[blkIndex].getCachedHosts()));
              }
            } else { // not splitable
              splits.add(makeSplit(path, 0, length, blkLocations[0].getHosts(),
                          blkLocations[0].getCachedHosts()));
            }
          } else { 
            //Create empty hosts array for zero length files
            splits.add(makeSplit(path, 0, length, new String[0]));
          }
        }
        // Save the number of input files for metrics/loadgen
        job.getConfiguration().setLong(NUM_INPUT_FILES, files.size());
        sw.stop();
        if (LOG.isDebugEnabled()) {
          LOG.debug("Total # of splits generated by getSplits: " + splits.size()
              + ", TimeTaken: " + sw.now(TimeUnit.MILLISECONDS));
        }
        return splits;
      }
    复制代码

    切片大小计算方法

    ①其中minSize默认为1,maxSize默认为long的最大值。根据公式,切片大小默认就等于blockSize大小。

    ②如果想切片大小大于块大小,则配置参数,使minSize > blockSize;如果想切片小于块大小,则配置参数,使maxSize < blockSize。

      protected long computeSplitSize(long blockSize, long minSize,
                                      long maxSize) {
        return Math.max(minSize, Math.min(maxSize, blockSize));
      }

    本文来自博客园,作者:秋华,转载请注明原文链接:https://www.cnblogs.com/qiu-hua/p/14179748.html

  • 相关阅读:
    处理某客户p570硬盘故障所思
    Android手机使用WIFI及USB建立FTP服务器总结
    Metro界面的真正意义
    找工作之面试血泪史
    vim7.4官方源码在vs2013的编译方法及问题总结
    关于vs2012/2013的C编译器生成的exe的向后兼容xp的问题
    【转】一篇关于32位Linux内核使用大内存的文章——Hugemem Kernel Explained  &nb
    直接修改Android软件数据库来改变软件设置实例一则
    解决MyEclipse中安装或升级ADT之后SDK Target无法显示的问题
    国行Android手机使用google全套GMS服务小结
  • 原文地址:https://www.cnblogs.com/qiu-hua/p/14179748.html
Copyright © 2011-2022 走看看