コレクションクラスの利用
前回紹介したfilter関数やforeach関数など、Scalaのコレクションライブラリ(Array,List,Set,Map)は高階関数と密接な関係があります。
Listクラスで定義されている代表的な関数を紹介します。
| 関数 | 説明 |
| filter(p: (A) ⇒ Boolean) | 引数の関数オブジェクトがtrueを返す要素のみ抽出したListを返す |
| foreach(f: (A) ⇒ Unit): Unit | Listの個々の要素に対して引数の関数を呼び出す |
| map[B](f: (A) ⇒ B): List[B] | Listの個々の要素を引数の関数に与えた結果に変換されたListを返す |
filter関数
filter関数は、引数に「条件を判断する関数オブジェクト」を与えることで、Listの中から任意の条件に適合する要素を取り出すことができます。
scala> val list = List( 1,2,3,4,5,6,7,8,9,10 )
list: List[Int] = List(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
scala> list.filter{ n => n % 2 == 0 }
res1: List[Int] = List(2, 4, 6, 8, 10)
例では、1から10までの整数を要素として持つListから、偶数のものを抽出しています。
「n => n % 2 == 0」が、偶数であるか判断する関数オブジェクトを関数リテラルで生成して渡しています。条件を奇数に変更するならば、「 n => n % 2 == 1」とすればよいわけです。
引数は、「Int型を受け取ってBoolean型を返す関数オブジェクト」ならばなんでもよいので、冒頭に例として出したisEven関数を渡しても問題ありません。
scala> list.filter( isEven ) res2: List[Int] = List(2, 4, 6, 8, 10)
foreach関数
foreach関数は、Listの要素それぞれを引数の関数に渡します。いわばListの繰り返し処理にあたります。
scala> list.foreach{ n => print( n + "," )}
1,2,3,4,5,6,7,8,9,10,
map関数
map関数は、Listの個々の要素を与えられた関数オブジェクトによって変換された、新しいListを生成して返します。
例えば、Listの個々の要素を2倍にするには、次のようにmap関数を利用します。
scala> list.map{ n => n * 2 }
res3: List[Int] = List(2, 4, 6, 8, 10, 12, 14, 16, 18, 20)
map関数で生成される新しいListは、必ずしも元のリストと同じ要素型である必要はありません。次のように、Int型をもつListからString型のListをmap関数で生成することができます。
を生成する]
scala> list.map{ n => n + "です" }
res4: List[java.lang.String] = List(1です, 2です, 3です, 4です, 5です, 6です, 7です, 8です, 9です, 10です)
filter,map,foreachの組み合わせ
filter関数、map関数はそれぞれList型を返すので、filter関数を適用した結果をさらにmap関数で変換してforeachで処理させる、といったようにつなげて利用することが可能です。
以下の例は、filter関数によって偶数の要素のみ抽出し、map関数で要素を2倍し、それぞれの要素をprintln関数で出力しています。
scala> list.filter { n => n % 2 == 0 }.map{ n => n * 2 } foreach { n => println( n ) }
4
8
12
16
20
さらに、これらの高階関数は、前回解説した「_」によるプレースホルダー引数でさらに省略して書くことができます。
「_」によるプレースホルダー引数は、無名関数の引数を「_」といういわば無名変数でかわりに受け取ることができるものです。filter関数に渡していた「n => n % 2 == 0」は、仮引数nを「_」に置き換えて「_ % 2 == 0」 と書くことができます。
scala> list.filter{ _ % 2 == 0 }.map { _ * 2 }.foreach{ println }
4
8
12
16
20
最後のforeachに渡す関数は、一引数の関数の場合は関数名だけでよいので、このように省略して書くことができるのです。
