2017-01-25 53 views
1

我有這樣的數據:如何從List [Map [String,String]]中提取值?

val data = List(Map(event_id -> ABC, event_name -> visited, timestamp -> 1478187513, member_id -> 111, category -> web, field1 -> abc), 
    Map(event_id -> DEF, event_name -> added, timestamp -> 1478187520, member_id -> 111), 
    Map(event_id -> ABC, event_name -> visited, timestamp -> 1478187522, member_id -> 111, category -> web, field1 -> abc), 
    Map(event_id -> ABC, event_name -> visited, timestamp -> 1478187618, member_id -> 111, category -> web, field1 -> abc)) 

我如何可以提取member_id並從中field1?問題是member_id存在於所有條目中,而field1 - 不是。

我想這一點,但它並沒有編譯說Type mismatch: expected String, actual Int

val member_id = data.flatMap(_.lift(0)).getOrElse("member_id", "") 
+0

如果'field1'不存在,你想怎麼做?返回類型是'Seq [(String,Option [String])]'你想要什麼? – mdm

+0

@mdm:不,我需要兩個String值作爲返回:'member_id'和'field1',如果沒有'field1',可以是一個空字符串(「」)。 – Dinosaurius

+0

但你可以有'member_id'多個條目,對吧?這是一個List [Map []]'。 – mdm

回答

1

我認爲這將工作:

data.collect{ 
    case map if map.keySet.contains(field1) => (map(member_id),map(field1)) 
}.headOption 

它會返回一個Option[(String, String)]。我假設1)總是有一個member_idmember_id都是一樣的,你只關心第一個與field1。如果情況並非如此,則會引發異常。

此外,如果你確信你將有至少一個條目,將符合你的標準,你也可以提取直接的字段:

val (memberId, fieldOne) = data.collect{ 
    case map if map.keySet.contains(field1) => (map(member_id),map(field1)) 
}.head 

再次,應該有不匹配的標準值初始集合head將引發異常。

編輯以應對最新評論

val (memberId, fieldOne) = data.collect{ 
    case map if map.keySet.contains(field1) => (map(member_id),map(field1)) 
}.headOption.getOrElse((data.head(member_id),"")) 

這將返回fieldOne="",與memberId設置爲正確的值,假設有初始List至少一個條目。雖然這很脆弱。

+0

是否可以單獨獲取'val member_id = ...'和'val field1 ='?編輯 – Dinosaurius

+0

以添加提取。這是你需要的嗎?我不確定我是否理解這個問題 – mdm

+0

這幾乎是我所需要的。謝謝。但是,如果沒有'field1',是否有可能返回'field1 =「」',而不是拋出異常?其餘的是絕對正確的,符合我的問題。 – Dinosaurius

相關問題