NLineInputFormat无法在Spark中运行

时间:2016-10-29 14:53:42

标签: scala hadoop apache-spark

我想要的基本上是让每个数据元素由10行组成。但是,使用以下代码,每个元素仍然是一行。我在这做什么错?

val conf = new SparkConf().setAppName("MyApp")
conf.set("spark.serializer", "org.apache.spark.serializer.KryoSerializer")
conf.registerKryoClasses(Array[Class[_]](classOf[NLineInputFormat], classOf[LongWritable], 
 classOf[Text]))
val sc = new SparkContext(conf)

val c = new Configuration(sc.hadoopConfiguration)
c.set("lineinputformat.linespermap", 10);
val data = sc.newAPIHadoopFile(fname, classOf[NLineInputFormat], classOf[LongWritable], 
 classOf[Text], c)

1 个答案:

答案 0 :(得分:4)

NLineInputFormat设计只是doesn't perform operation you expect it to

  

NLineInputFormat,它将N行输入拆分为一个拆分。 (...)拆分输入文件,以便默认情况下,一行作为值提供给一个地图任务。

正如您所看到的,它会修改如何计算拆分(Spark命名法中的分区),而不是如何确定记录。

如果描述不清楚,我们可以通过以下示例说明:

def nline(n: Int, path: String) = {
  val sc = SparkContext.getOrCreate
  val conf = new Configuration(sc.hadoopConfiguration)
  conf.setInt("mapreduce.input.lineinputformat.linespermap", n);

  sc.newAPIHadoopFile(path,
    classOf[NLineInputFormat], classOf[LongWritable], classOf[Text], conf
  )
}

require(nline(1, "README.md").glom.map(_.size).first == 1)
require(nline(2, "README.md").glom.map(_.size).first == 2)
require(nline(3, "README.md").glom.map(_.size).first == 3)

如上所示,每个分区(可能不包括最后一个分区)恰好包含n行。

虽然您可以尝试对其进行改造以适合您的情况,但不建议您使用linespermap参数的小值。