Apache spark 筛选阶段在RDD沿袭重新执行中丢失

Apache spark 筛选阶段在RDD沿袭重新执行中丢失,apache-spark,Apache Spark,我有一个关于RDD和谱系图的问题。让我举例说明: 我有一个如下所示的数据文件: ID; parent; level; type;content; Budget; 999999 ;;a;Total;total; 313344394; 01 ;;a;Part 1;Chancellery of the President of the Republic of Poland; 171524; 02 ;;a;Part 2;Chancellery of the Sejm; 430780; 03 ;;a;Pa

我有一个关于RDD和谱系图的问题。让我举例说明: 我有一个如下所示的数据文件:

ID; parent; level; type;content; Budget;
999999 ;;a;Total;total; 313344394;
01 ;;a;Part 1;Chancellery of the President of the Republic of Poland; 171524;
02 ;;a;Part 2;Chancellery of the Sejm; 430780;
03 ;;a;Part 3;OFFICE OF THE SENATE; 176212;
04 ;;a;Part 4;SUPREME COURT; 88161;
请注意,对于最后一个预算字段,有一个前导空格。 因此,我读入数据,创建一个由选定列组成的RDD:

scala>  val baseRDD=sc.textFile(dataFile)
baseRDD: org.apache.spark.rdd.RDD[String] = MapPartitionsRDD[103] at textFile at <console>:29

scala> val budgetRDD=baseRDD.map(_.split(";")).map(x => (x(0),x(4), x(5))) 
budgetRDD: org.apache.spark.rdd.RDD[(String, String, String)] = MapPartitionsRDD[101] at map at <console>:31
这是可以理解的,因为预算栏中有前导空格。 因此,我没有使用trim,而是编辑并删除了数据文件中的前导空格:

ID; parent; level; type;content;Budget;
999999 ;;a;Total;total;313344394;
01 ;;a;Part 1;Chancellery of the President of the Republic of Poland;171524;
02 ;;a;Part 2;Chancellery of the Sejm;430780;
03 ;;a;Part 3;OFFICE OF THE SENATE;176212;
04 ;;a;Part 4;SUPREME COURT;88161;
进行了此更改后,对于上面的沿袭图,我的期望是重新运行
take
操作将重新执行沿袭图并产生所需的结果。但事实并非如此,相反,我得到了另一个错误,表明没有应用排除标题行的筛选步骤:

scala> idBudgetRDD.take(2)
16/02/12 03:47:03 ERROR Executor: Exception in task 0.0 in stage 147.0 (TID 180)
java.lang.NumberFormatException: For input string: "Budget"
at     java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
at java.lang.Integer.parseInt(Integer.java:580)
at java.lang.Integer.parseInt(Integer.java:615)

有人能解释发生了什么事吗?我的想法是,由于延迟求值和沿袭,修复数据文件并重新执行
take
将导致沿袭图整体重新运行。

结果是我上面使用的过滤器已修复,因此在修改文件后,它不再适用。我可以通过指定一个依赖于匹配ID字符串的筛选器来解决此问题,如下所示:

val idBudgetRDD = budgetRDD.filter(! _.0.startsWith("ID;")).map{case(id,name,money) => (id, money.toInt)} 

这始终与标题行匹配,重新运行take会产生正确的结果。

您的
headerRow
变量包含什么?抱歉,我错过了这一行,并将其添加到上面:
val headerRow=budgetRDD。首先
在再次执行
take
之前是否更新了此变量?啊,现在我明白了。headerRow变量在具体化后需要更新。我犯了错误,谢谢。我假设如果我用类似于
val dataRows=budgetRDD.filter(!=budgetRDD.first)
的东西替换过滤器步骤中的变量,这可能会起作用。我尝试使用上面的过滤器,并得到以下错误:
16/02/12 05:14:47警告TaskSetManager:在阶段149.0(TID 182,localhost)中丢失任务0.0:org.apache.spark.SparkException:RDD转换和操作只能由驱动程序调用,不能在其他转换内部调用;例如,rdd1.map(x=>rdd2.values.count()*x)无效,因为无法在rdd1.map转换内部执行值转换和计数操作。有关更多信息,请参阅SPARK-5063。
有什么建议吗?
scala> idBudgetRDD.take(2)
16/02/12 03:47:03 ERROR Executor: Exception in task 0.0 in stage 147.0 (TID 180)
java.lang.NumberFormatException: For input string: "Budget"
at     java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
at java.lang.Integer.parseInt(Integer.java:580)
at java.lang.Integer.parseInt(Integer.java:615)
val idBudgetRDD = budgetRDD.filter(! _.0.startsWith("ID;")).map{case(id,name,money) => (id, money.toInt)}