Webサイト制作コースのお申し込みはこちら

Java8 で追加された Steam API により、これまで何行にも渡って書かれ、冗長になりがちだったソート処理を簡潔に記述することが可能になりました。

この記事では、リストなどのコレクションを、Steam API とラムダ式を使ってソートする方法を解説します。

基本のソート

最初は、intchar などの基本データ型(プリミティブ型)のコレクションをソートして、Steam API でのソートのイメージを掴みましょう。

次のサンプルコードは、数値のリストを昇順に並べる例です。Steam API では、Stream#sort メソッド使用してコレクションのソートを行っていきます。

//↓以下の import が必要
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import static java.util.Comparator.*;

List<Integer> list = new ArrayList<Integer>(Arrays.asList(30, 20, 50, 10));
list.sort(naturalOrder());
// 10, 20, 30, 50

降順にソートする場合は、メソッドの引数に reverseOrder を指定します。

list.sort(Comparator.reverseOrder())
ポテパンダの一言メモ

Java8 以前は、ソートするオブジェクトに Comparable インタフェースを実装する必要がありましたが、Steam API の登場によって、非常にシンプルなコードでソートが可能になりました。

文字列(String)のソート

String 型のリストも、基本データ型の時と同様に、値を格納したリストに対しStream#sort メソッドを呼び出せば、文字コード順にソートできます。

String[] strs = {"AA", "aa", "BB", "bb", "CC", "cc"};

List<String> list = Arrays.asList(strs.clone());
list.sort(naturalOrder());
// "AA", "BB", "CC", "aa", "bb", "cc"

通常、文字列のソートを行う場合は、英字は大文字、小文字は区別され、大文字のA-Z →小文字の a-z の順にソートが行われますが、StringクラスのCASEINSENSITIVEORDERを引数に渡すと、大文字、小文字の区別を行わずにソートできます。

実際に試してみましょう。

String[] strs = {"AA", "aa", "BB", "bb", "CC", "cc"};

List<String> list = Arrays.asList(strs.clone());
list.sort(String.CASE_INSENSITIVE_ORDER);
// "AA", "aa", "BB", "bb", "CC", "cc"

オブジェクトのソート

独自に作成したクラスなどのオブジェクトも、任意のキーを指定して、コレクションをソートできます。 オブジェクトをソートする場合は、ソートキーとなるプロパティなどをjava.util.Comparator#comparing で指定します。

単項目のキーでオブジェクトをソート

次のコードは、User クラスのscoreプロパティをキーに、オブジェクトを降順でソートする例です。

List<User> list = new ArrayList<>();
//       new User(氏名、ランク、スコア)
list.add(new User("Yamada", 1, 50));
list.add(new User("Sato", 1, 20));
list.add(new User("Hayashi", 2, 10));
list.add(new User("Abe", 2, 40));

//スコアの降順でソート
list.sort(comparing(User::getScore).reversed());

//ソートした結果を表示
for (User user : list) {
  System.out.println(String.format("%s:%d", user.getName(), user.getScore()));      
}
// Yamada:50
// Abe:40
// Sato:20
// Hayashi:10

また、上のコードは、ラムダ式を使って次のようにも書くことができます。

list.sort(comparing((User x) -> x.getScore()).reversed());

複数キーでのソート

ソートキーが複数ある場合は、thenComparingメソッドを使用してソートキーを複数指定します。次のサンプルコードは、ランクの昇順、スコアの降順でコレクションをソートする例です。

List<User> list = new ArrayList<>();
list.add(new User("Yamada", 1, 50));
list.add(new User("Sato", 1, 20));
list.add(new User("Hayashi", 2, 10));
list.add(new User("Abe", 2, 40));

// ランクの昇順、スコアの降順でリストを並び替え
list.sort(comparing(User::getRank).thenComparing(comparing(User::getScore).reversed()));

for (User user : list) {
  System.out.println(String.format("%s rank=%d score=%d",
                                   user.getName(), user.getRank(), user.getScore()));      
}

//Yamada rank=1 score=50
//Sato rank=1 score=20
//Abe rank=2 score=40
//Hayashi rank=2 score=10

最後に今回使用した User クラスの定義を載せておきます。

public class User {

  //ユーザ名
  public String name;
  //ランク
  public int rank;
  //スコア
  public int score;

  public User(String name, int rank, int score) {
    this.name = name;
    this.rank = rank;
    this.score = score;
  }

  public String getName() {
    return name;
  }
  public int getRank() {
    return rank;
  }
  public int getScore() {
    return score;
  }
}

まとめ

Java8 で追加された Steam API で、コレクションをソートする方法を解説しました。

Steam API をうまく活用することで、これまで冗長的になりがちだった Java のコードを、よりシンプルに分かりやすく記述することが可能になりました。

Steam API については、以下の記事でも紹介しているため、こちらもご覧ください。

【関連記事】
Java Stream API (ストリームAPI)を使ってみよう

エンジニアになりたい人に選ばれるプログラミングスクール「ポテパンキャンプ 」

ポテパンキャンプは卒業生の多くがWebエンジニアとして活躍している実践型プログラミングスクールです。 1000名以上が受講しており、その多くが上場企業、ベンチャー企業のWebエンジニアとして活躍しています。

基礎的な学習だけで満足せず、実際にプログラミングを覚えて実践で使えるレベルまで学習したいという方に人気です。 プログラミングを学習し実践で使うには様々な要素が必要です。

それがマルっと詰まっているポテパンキャンプでプログラミングを学習してみませんか?

卒業生の多くがWebエンジニアとして活躍

卒業生の多くがWeb企業で活躍しております。
実践的なカリキュラムをこなしているからこそ現場でも戦力となっております。
活躍する卒業生のインタビューもございますので是非御覧ください。

経験豊富なエンジニア陣が直接指導

実践的なカリキュラムと経験豊富なエンジニアが直接指導にあたります。
有名企業のエンジニアも多数在籍し品質高いWebアプリケーションを作れるようサポートします。

満足度高くコスパの高いプログラミングスクール「ポテパンキャンプ」

運営する株式会社ポテパンは10,000人以上のエンジニアのキャリアサポートを行ってきております。
そのノウハウを活かして実践的なカリキュラムを随時アップデートしております。

代表の宮崎もプログラミングを覚えサイトを作りポテパンを創業しました。
本気でプログラミングを身につけたいという方にコスパ良く受講していただきたいと思っておりますので、気になる方はぜひスクール詳細をのぞいてくださいませ。