Java入門

【Java入門】ラムダ式とStream API

  1. HOME >
  2. 開発 >
  3. Java >
  4. Java入門 >

【Java入門】ラムダ式とStream API

前回の記事では、Java APIについて紹介しました。

本記事では、ラムダ式とStream APIについて紹介します。

ラムダ式とは

ラムダ式とは、Java 8から追加された新しい文法で、関数型プログラミングの概念を取り入れ、匿名関数を簡潔に表現する方法を提供します。

ラムダ式は次のような構文で記述します。

(型1 引数名1, 型2 引数名2, ....) -> {
    ....ラムダ式本体の処理....
}

何を書いているのかわからない...

ラムダ式を使う理由は以下です。

  • 記述を簡潔にできる
  • ラムダ式を前提に用意されたStream APIが使える

「Stream API」は非常に便利なAPIなので、使い方を覚えておきましょう。

これまでfor文でループしていた処理を簡潔に記述できます。

Stream APIとは

Stream APIとは、関数型プログラミング用のライブラリで、データを流し込み簡単に加工できるようになっています。

Java8から追加されたAPIで、今までコレクションに対して行っていた煩雑な処理を簡潔なコードで記述することが可能になりました。

次の例は、Stream APIを使い、次の条件に一致する人物をコンソールに出力しています。

  • 30歳以上の人物
  • 「order」の昇順に並び替える
  • コンソールに出力するのは「name」だけ
import java.util.List;

public class StreamApiSample {

	public record Names(String name, int age, int order) {
	}

	public static void main(String[] args) {
		
		List<Names> list = List.of(
				new Names("山田太郎", 66, 3),
				new Names("山田次郎", 50, 1),
				new Names("山田三郎", 33, 4),
				new Names("山田四郎", 18, 2)
		);
		
		List<String> resultList = list.stream()
				// 30歳以上の人物を抽出
				.filter(n -> n.age >= 30)
				// orderの昇順で並び変える
				.sorted((s1, s2) -> s1.order-s2.order)
				// nameのみ抽出する
				.map(n -> n.name)
				// Listに変換する
				.toList();
		
		resultList.forEach(System.out::println);
	}
}

これまでは、for文等を使い対象レコードを抽出する必要がありましたが、Stream APIの登場により、上記例のように処理を簡潔に書けるようになりました。

主なStream APIの使い方は次のとおりです。

filter()

filterでは、データの中から指定した条件に一致するものを抽出します。

例えば、次のリストから「"い"」を含むデータだけを抽出するとします。

List<String> list = new ArrayList<String>();
list.add("にんじん");
list.add("じゃがいも");
list.add("きゃべつ");
list.add("さつまいも");

[Stream APIを使わない場合の例]

public class StreamApiSample {
	
	public static void main(String[] args) {
		
		List<String> list = new ArrayList<String>();
		list.add("にんじん");
		list.add("じゃがいも");
		list.add("きゃべつ");
		list.add("さつまいも");
		
		// streamAPIを使わない場合
		List<String> resultList = new ArrayList<String>();
		for(String t : list) {
			if (t.contains("い")) {
				resultList.add(t);
			}
		}
	}
}

[Stream APIを使う場合の例]

public class StreamApiSample {

	public static void main(String[] args) {
		
		List<String> list = new ArrayList<String>();
		list.add("にんじん");
		list.add("じゃがいも");
		list.add("きゃべつ");
		list.add("さつまいも");
		
		// streamAPIを使った場合
		List<String> resultList = list.stream().filter(t -> t.contains("い")).toList();
	}
}

Stream APIを使わない場合は、for文で対象データを抽出する必要がありましたが、Stream APIを使う場合は、上記例のように簡潔に記述できます。

ここがポイント

  • stream():コレクションをストリームに変換する
  • filter():引数のラムダ式がtrueのデータを抽出する
  • toList():ストリームをコレクションに変換する

map()

mapは個々のデータを変換して、新しいデータを作ります。

次はmapの使用例です。リスト内の文字数を出力しています。

[mapの使用例]

public class StreamApiSample {

	public static void main(String[] args) {
		
		List<String> list = new ArrayList<String>();
		list.add("test");
		list.add("test123");
		list.add("test12345");
		
		// streamAPIを使った場合
		list.stream().map(t -> t.length()).forEach(System.out::println);
	}
}

[出力結果]

4
7
9

Stream APIのmap()で文字数に変換し、forEach(System.out::println)で文字数をコンソールに出力しています。

ここがポイント

  • stream():コレクションをストリームに変換する
  • map():引数に変換処理内容のラムダ式を記述する

sorted()

sortedは、データを並び替えます。

次はsortedの使用例です。リスト内のデータを昇順に並び替えています。

[sortedの使用例]

public class StreamApiSample {

	public static void main(String[] args) {
		
		List<Integer> list = new ArrayList<Integer>();
		list.add(23);
		list.add(88);
		list.add(10);
		list.add(5);
		
        // 昇順に並び替える 
		list.stream().sorted((s1, s2) -> s1-s2).forEach(System.out::println);
	}
}

[出力結果]

5
10
23
88

Stream APIのsorted()で並び替えをおこない、forEach(System.out::println)で並び替えた結果をコンソールに出力しています。

ここがポイント

  • stream():コレクションをストリームに変換する
  • sorted():引数のラムダ式が正のときは昇順、負のときは降順にデータを並び替える

reduce()

reduceは、データを1つずつ評価していき、結果に集約します。

次はreduceの使用例です。金額の合計を求めています。

[reduceの使用例]

public class StreamApiSample {

	public static void main(String[] args) {
		
		List<Integer> list = new ArrayList<Integer>();
		list.add(10023);
		list.add(1088);
		list.add(2210);
		list.add(25);
		
		// streamAPIを使った場合
		long sum = list.stream().reduce(0, (a,x) -> a+x);
		System.out.println(sum);
	}
}

[出力結果]

13346

Stream APIのreduce()で金額の合計を求め、System.out.printlnで結果をコンソールに出力しています。

ここがポイント

  • stream():コレクションをストリームに変換する
  • reduce():第1引数は初期値。第2引数で集約方法を指定する。

helpful

-Java入門