2015-10-14 45 views
-1

我有一個名爲vertexDict一個文本文件,其中有由「\ 1」分裂多個鍵值對外界附加價值,我需要將其轉換爲一個地圖在我的火花program.Here是我的代碼:階VAR未能獲得foreach循環

var mapDict = Map[Long, String]() 
sc.textFile(vertexDict).map(line=> line.split("\1")).foreach(a=>{ 
    if(a.length ==2){ 
    mapDict += a(0).toLong->a(1) 
    } 
}) 

問題是mapDict仍然foreach循環結束後空的,但我debuged進入循環,並mapDict成功添加元素到它,因此我通過繞過這個問題:

val mapDict = sc.textFile(vertexDict).map(line=> line.split("\1")).map(a=>a(0).toLong->a(1)).collect().toMap 

它的工作原理。但我仍然不知道爲什麼foreach未能添加。 謝謝!

+1

的' 「\ 1」'不編譯。你能粘貼實際的代碼嗎? – Jus12

+0

「\ 1」只是一個我使用的分隔符,可以是任何東西。這是我的實際代碼,代碼的其他部分是巨大的,並且對此問題沒有任何影響。 – seabiscuit08

+0

您的需要mapDict是可變的附加價值給它 – Hackaholic

回答

0

似乎有一些問題,你的邏輯。正確的邏輯是:

var mapDict = Map[Long, String]() 
val str = "1234\1hello\n3456\1world" 
str.lines.foreach{line => 
    val a = line.split("\1") 
    if(a.length == 2) { 
    mapDict += (a(0).toLong->a(1)) 
    } 
} 

這裏是輸出:

scala> mapDict foreach println 
(1234,hello) 
(3456,world) 
0

這是一個相當迫切的問題解決辦法。 FP方法是將其視爲線的集合,從中想要生成從符合特定標準(此處爲兩項)的線獲取的地圖。嘗試:

val str = "1234\1hello\nNonmatching line\n3456\1world\nAline\1with too\1many matches" 
val mapDict = str.lines.map(a => a.split("\1")).collect {case Array(k,v) => k->v}.toMap 

我添加了1條項目和3條項目來證明它們被過濾掉。這給出:

mapDict: scala.collection.immutable.Map[String,String] = Map(1234 -> hello, 3456 -> world) 

請注意,您不需要mapDict是一個var更多。

0

我終於知道爲什麼修改foreach循環的地圖收集不起作用:因爲火花運行並行和地圖收集在不同的分區改變,我在我的問題粘貼的解決方案只需使用RDD操作收集得到所有分區數據到驅動程序並在本地運行到映射。 所以解決方法是使用火花累加器。