Collections クラスの便利メソッド
並べ替えを自分で書くと、境界を 1 つ間違える
リストを昇順にしたいだけなのに、交換用の一時変数と二重ループを書き、添字の範囲を 1 つ間違えて悩む。誰もが一度は通る道ですが、java.util.Collections を使えばこの手の処理は 1 行で終わります。
Java
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
List<String> names = new ArrayList<>();
names.add("sato");
names.add("abe");
names.add("kudo");この names に対して、並べ替えと最大値の取得を呼んでみます。
Java
Collections.sort(names);
System.out.println(names); // [abe, kudo, sato]
System.out.println(Collections.max(names)); // satoCollections.sort はその型の標準的な順番、つまり数値なら小さい順、文字列なら辞書順に並べ替えます。Collections.max はその順番でいちばん後ろにあたる要素を返します。Integer String LocalDate のように比べ方が決まっている型なら、そのまま渡すだけです。
Collections(s 付き) とCollection(s 無し) は別物です。前者は便利メソッドを集めた道具箱、後者はListやSetの親インタフェースです。
sort は新しいリストを返さない
Collections.sort の戻り値は void です。
Java
List<String> sorted = Collections.sort(names); // コンパイルエラー並べ替えは、元のリストをその場で書き換える形で行われます。呼んだあとの names がもう並んでいるので、受け取る変数は要りません。並べ替えた結果が返ってくると思い込んでいると、この 1 行で止まります。
配列のままでは渡せない
Collections のメソッドは List を受け取ります。Collections.sort(arr) のように int[] を渡してもコンパイルは通りません。ジェネリクスにプリミティブ型は入れられないので、List<int> という型そのものが存在しないからです。
そのため int[] を扱うときは、まず List<Integer> を用意して中身を 1 つずつ移し替えます。移し終われば、上の例と同じように sort も max も呼べます。
もう 1 つ気をつけたいのが、空のリストに Collections.max を呼ぶと NoSuchElementException で落ちることです。最大値は要素が 1 つ以上あることが前提なので、空かどうかを先に確かめてから呼びます。課題でも、空の配列が渡されたときの戻り値が別に決められています。順番としては、まず空の場合を片付け、それから詰め替えに進むと迷いません。
要件
- クラス名は
Solution、メソッド名はsortAndMax、引数はint[] arrひとつにすること - 戻り値の型は
intで、int[]をList<Integer>に変換してからCollections.sortとCollections.maxを使って最大値を返すこと - 配列が空 (
arr.length == 0) のときは-1を返すこと (Collections.maxを空リストに呼ぶと例外になるため必ずガードする)
入出力例
sortAndMax([3,1,4,1,5]) → 5
sortAndMax([100]) → 100
sortAndMax([]) → -1
sortAndMax([-5,-10,-1]) → -1
sortAndMax([7,7,7,7]) → 7
sortAndMax([1,2,3,4,5]) → 5