Scala collectons使用包含地图的对象对序列进行过滤和排序,然后对其进行迭代

时间:2014-09-22 08:58:53

标签: scala sorting collections filter collect

给出一个对象:

 case class GT(code: String,names: Map[String, Option[String]]) {}

列表:

val gText = List(new GT("USB", Map("de" -> Some("a"), "en" -> Some("abc"), "fr" -> Some("ab"))),
                  new GT("Switch", Map("de" -> Some("abcdef"), "en" -> Some("b"), "fr" ->  
                          Some("abc"), "es" -> Some("abc"))),
                  new GT("PVC", Map("de" -> Some("abc"), "en" -> Some("bc"), "fr" -> Some("abcd"))))

我想迭代gText列表,但是依赖于地图“names”的键,并且按照每个“names”映射值的长度的降序排列。

第一次迭代应该在下面的oder中,其值为“de”:

1. code: "Switch" & names.key="de" & names.value = Some("abcdef")
2. code: "PVC" & names.key="de" & names.value = Some("abc")
3. code: "USB" & names.key="de" & names.value = Some("a")

第二次迭代应该在下面的oder中,其值为“en”:

1. code: "USB" & names.key="en" & names.value = Some("abc")
2. code: "PVC" & names.key="en" & names.value = Some("bc")
3. code: "Switch" & names.key="en" & names.value = Some("b")

第三次迭代应该在下面的oder中,其值为“fr”:

1. code: "PCV" & names.key="fr" & names.value = Some("abcd")
2. code: "Switch" & names.key="fr" & names.value = Some("abc")
3. code: "Switch" & names.key="fr" & names.value = Some("ab")

上次迭代适用于names.key="es" code="Switch"& names.key="es"names.value = Some("abc")

如上所述,主要目标是根据每个值的长度迭代不同GT的相同键的值。

我该怎么做?也许首先我必须在另一组中收集密钥,然后过滤和sortyBy。欢迎任何建议。

提前致谢。 的Ugur

2 个答案:

答案 0 :(得分:1)

val gtEntries = gText.flatMap( gt => gt.names.toList.map(entry => (gt.code, entry._1, entry._2)))
val gtEntriesByLang = gtEntries.groupBy(_._2)

for (lang <- gtEntriesByLang.keys.toList.sorted;
 gtEntry <- gtEntriesByLang(lang).sortBy(entry => -entry._3.map(_.length).getOrElse(0) ))
 {
    println(gtEntry)
 }

第一行&#39;变平&#39;将GT列表转换为表单元组(&#34; USB&#34;,&#34; en&#34;,Some(&#34; abc&#34;))。

第二行按语言i分组。即&#34;恩&#34; =&GT;列表((&#34; USB&#34;,&#34; en&#34;,一些(&#34; abc&#34;),...)

for comprehension按降序顺序浏览所有语言,然后按原始名称映射的值的长度对条目进行排序(如果选项未定义,则为0;如果要与None不同,则将其设为1 #34;&#34;。)

答案 1 :(得分:1)

我不太清楚你想要什么样的迭代顺序,但这是另一种皮肤猫的方法。

  val countrySet = gText.flatMap { _.names.keys }.toSet 
  for {
    c <- countrySet
    gc = gText.filter(_.names.contains(c))
    g <- gc.sortBy(_.names(c).get.length).reverse
  } println("country " + c + " " + g)

获取一组国家/地区。然后,遍历这些,将列表过滤为仅具有当前国家/地区条目的列表,按相应值的长度对该列表进行排序(反转,以获得下降长度)