listに格納したデータを一定の並び順に変更したい場合、ソート処理を利用することで簡単に実現が可能です。
本記事では、Javaプログラム開発に欠かせないlistのソート処理の方法について、サンプルコードを交えながらご紹介していきます。
Javaのlistを昇順・降順でソートする
Javaのlistインターフェースを実装したコレクションクラス(ArrayListなど)では、「sort」メソッドを利用することで要素の並び替えを行うことが可能です。
Java7以前の主な記述法
早速サンプルでsortメソッドの動きを確認していきましょう。
Java7以前では、Collectionsクラスのsortメソッドにリストを指定することでソート処理を実施する方法が一般的でした。
package test; import java.util.ArrayList; import java.util.Collections; public class Main { public static void main(String[] args) { ArrayList<String> strList = new ArrayList<>(); strList.add("うま"); strList.add("うし"); strList.add("あり"); strList.add("いか"); System.out.println("ソート前: " + strList); Collections.sort(strList); // ソート処理 昇順 System.out.println("昇順ソート後: " +strList); Collections.sort(strList, Collections.reverseOrder()); // ソート処理 降順 System.out.println("降順ソート後: " +strList); } }
実行した結果が下記の通りです。
ソート前: [うま, うし, あり, いか] 昇順ソート後: [あり, いか, うし, うま] 降順ソート後: [うま, うし, いか, あり]
昇順にソートを行う場合、引数にリストを指定するだけでよく、降順にソートを行いたい場合には第2引数にCollectionsクラスのreverseOrderメソッドを指定することで実現可能です。
Java8以降の主な記述法
Java8以降では、listのソートにはComparatorを利用する方法主流となります。
特にStreamを使用して、元のコレクションと別のコレクションを作成出来る機能は大きなメリットです。
上記のJava7以前のサンプルをComparatorを利用して記述し直してみましょう。
package test; import java.util.ArrayList; import java.util.Comparator; import java.util.List; import java.util.stream.Collectors; public class Main { public static void main(String[] args) { ArrayList strList = new ArrayList(); strList.add("うま"); strList.add("うし"); strList.add("あり"); strList.add("いか"); System.out.println("ソート前: " + strList); List absList = strList.stream().sorted(Comparator.naturalOrder()).collect(Collectors.toList()); // ソート処理 昇順 System.out.println("昇順ソート後: " + absList); List descList = strList.stream().sorted(Comparator.reverseOrder()).collect(Collectors.toList()); // ソート処理 降順 System.out.println("降順ソート後: " + descList); System.out.println("元のリスト状態を確認: " + strList); } }
実行した結果が下記の通りです。
ソート前: [うま, うし, あり, いか] 昇順ソート後: [あり, いか, うし, うま] 降順ソート後: [うま, うし, いか, あり] 元のリスト状態を確認: [うま, うし, あり, いか]
「stream().sorted」を利用することにより、ソート処理前のリストと異なるコレクションクラスにソート結果を返却出来るようになりました。
昇順でソートを実施したい場合には「naturalOrder()」、降順でソートを実施したい場合には「reverseOrder()」を指定することで簡単に実現可能です。
Javaのlistを任意の形式でソートする
Javaのlistを「ユーザー定義のクラスに設定された値によって並び替えたい」「複数の条件を組み合わせて並び替えたい」など、単純な昇順・降順以外のルールを設定してソート処理を実施したいケースも存在します。
Java8では、Comparatorインターフェースを利用することで、任意の形式でソート処理を実施することが可能です。
複数条件を組み合わせたユーザー定義クラスのソート処理
複数条件でユーザー定義クラスのフィールド値によってソート順を切り替える処理のサンプルをご紹介していきます。
ユーザー定義クラスをキーとしてソート処理を実施したい場合には、「comparing()」を利用します。
複数条件を組み合わせる場合には、「thenComparing()」を利用することで、ソート条件を指定することが可能です。
package test; import java.util.ArrayList; import java.util.Comparator; import java.util.List; import java.util.stream.Collectors; public class Main { public static void main(String[] args) { List strList = new ArrayList(); strList.add(new Animal("ぽち", "いぬ")); strList.add(new Animal("たま", "ねこ")); strList.add(new Animal("たろう", "いぬ")); strList.add(new Animal("ぴよ", "とり")); System.out.println("ソート前: " + strList); Comparator animalComperator = Comparator.comparing(Animal::getType) .thenComparing(Comparator.comparing(Animal::getName)); // ソート条件作成 List absList = strList.stream().sorted(animalComperator) .collect(Collectors.toList()); // ソート処理 System.out.println("ソート後: " + absList); } } class Animal { private String name; private String type; public Animal(String name, String type) { this.name = name; this.type = type; } public String getName() { return name; } public String getType() { return type; } @Override public String toString() { return "type=" + type + " name=" + name; } }
実行した結果が下記の通りです。
ソート前: [type=いぬ name=ぽち, type=ねこ name=たま, type=いぬ name=たろう, type=とり name=ぴよ] ソート後: [type=いぬ name=たろう, type=いぬ name=ぽち, type=とり name=ぴよ, type=ねこ name=たま]
サンプルでは、Animalクラスのtypeフィールドの値を昇順に並び替えた後、nameフィールドの値を2つ目の条件として昇順で並び替えるよう指定しています。
18行目で、ソート順を定義するComparatorを作成し、21行目からの実際のソート処理に条件として指定しています。
さいごに: Java8以降のlistソート処理にはComparatorを利用しよう
本記事では、Javaでのlist要素を並び替えるソート処理について、Java7以前とJava8以降の主流の方法をご紹介してきました。
Java8以降でも引き続きCollectionsクラスを利用したソート処理も実装可能ではありますが、Comparatorを利用することで可読性向上や機能性向上などが期待出来ます。
今後Java8以降でシステム開発を行う際には、基本的にはComparatorを利用してソート処理を実装することをおすすめします。
似た処理にCollectionsクラスのreverseメソッドを利用する方法がありますが、reverseメソッドは要素を逆順にする処理であり、降順に並び替える処理ではありません。
降順に並び替えたい場合には、今回のようにsortメソッドの第2引数でreverseOrderを指定する方法で実行しましょう。