2010-02-06 2 views
11

Очень удобный код Ruby:Scala эквивалент карты Ruby.each?

some_map.each do |key,value| 
    # do something with key or value 
end 

Scala эквивалент:

someMap.foreach(entry => { 
    val (key,value) = entry 
    // do something with key or value 
}) 

Необходимость добавить дополнительные val линии ошибок меня. Я не мог понять, как указать функцию arg для извлечения кортежа, поэтому мне интересно, есть ли способ сделать это или почему нет foreach, который извлекает ключ и значение для меня?

ответ

19

Это работает, тоже:

someMap.foreach {case (key, value) => 
    // do something with key and/or value 
} 
+0

Заявление о действии действительно является частично скрытой функцией, поэтому это удобное сокращение сокращений. Это может помочь кому-то, кто озадачен ошибкой типа, которая возникает из-за несоответствия такого рода выражений. –

+0

Хорошая статья о частичных функциях здесь http://ebruchez.blogspot.com/2011/10/scala-partial-functions-without-phd.html – foolshat

11

Мне нравится этот один:

scala> val foo = Map(1 -> "goo", 2 -> "boo") 
foo: scala.collection.immutable.Map[Int,java.lang.String] = Map(1 -> goo, 2 -> boo) 

scala> for ((k,v) <- foo) println(k + " " + v) 
1 goo 
2 boo 
+0

Нет необходимости в 'val' внутри генератора' for'. –

5

Вам не нужно даже val в течение цикла:

Следуя примеру ViktorKlang в:

scala> val foo = Map(1 -> "goo", 2 -> "boo") 
foo: scala.collection.immutable.Map[Int,java.lang.String] = Map(1 -> goo, 2 -> boo) 

scala> for ((k, v) <- foo) println(k + " " + v) 
1 goo 
2 boo 

Обратите внимание, что for довольно мощный в Scala, так что вы можете также использовать его для sequence comprehensions:

scala> val bar = for (val (k, v) <- foo) yield k 
bar: Iterable[Int] = ArrayBuffer(1, 2) 
+0

'for' на самом деле является Monad Comprehension, замаскированным под цикл' for', чтобы не отпугивать Java-программистов такими понятиями, как * Monad *. (Точно так же, как понимание запросов в C#/VB.NET - это просто соображения монады, замаскированные под SQL-запросы.) Таким образом, это еще более мощно, чем понимание последовательности. –

+1

Jörg, не используйте слово М, это пугает людей ;-) –

+0

@ViktorKlang: Именно! Вот почему Мартин Одерски замаскировал их, как уже знают Java-программисты: цикл 'for'. И Эрик Мейер замаскировал их как SQL-запрос в C# и VB.NET, Дон Симе замаскировал их как конвейер оболочки Unix в F #, Саймон Пейтон Джонс замаскировал их как блок C в Haskell. (Иногда я думаю, что они были бы менее страшными, если бы они не скрывались в тени ...) –

2

Function.tupled преобразует функцию (a1, a2) => b) в функцию ((a1, a2)) => b.

import Function._ 
someMap foreach tupled((key, value) => printf("%s ==> %s\n", key, value)) 
Смежные вопросы