プロジェクトで作業しているときに、ある種のオブジェクトのコレクションを並べ替える必要が生じることがあります。そのために独自の並べ替えアルゴリズムを実装する必要があると思うかもしれませんが、これは多少不必要ですが、知っておくと損にはなりません。彼らがどのように働くのか。たとえば、整数の配列がある場合、プリミティブの配列を受け入れて昇順に並べ替える Arrays.sort() メソッドを使用できます。これは、結果を配列に代入する必要がないという事実を利用します。このメソッドは元の配列を変更するため、新しい変数。
int[] numbers = {9, 8, 5, 3, 1, 2, 4, 6, 7}; Arrays.sort(numbers); System.out.println(Arrays.toString(numbers)); // Output [1, 2, 3, 4, 5, 6, 7, 8, 9]
これは、カスタム オブジェクトのコレクション (たとえば、タイプ Movie のレコード) がある場合にも当てはまりますが、Arrays.sort() メソッドを見ると、このタイプのオブジェクトの配列は受け入れられないため、 T 型のオブジェクトと Comparator 型のオブジェクトをパラメータとして受け入れる sort() メソッドを使用します。スーパーT>これは機能的なインターフェイスです。 Java 内の他の多くのメソッドがカスタム方法でオブジェクトを比較するためにこのインターフェイスを使用するため、このインターフェイスは非常に重要です。たとえば、Collections.sort() メソッドや List オブジェクトの sort() メソッド、ストリームでも要素を並べ替えるための Comparator を受け入れます。
関数インターフェイス Comparator (機能的であるため、ラムダ式として記述できます) は、型 T の 2 つのオブジェクトを比較できるインターフェイスであり、整数、文字列、カスタムの比較に使用されます。オブジェクトなどこのインターフェイスにはいくつかの静的メソッドとデフォルト メソッドがありますが、重要なのは、2 つのオブジェクトを比較するために実装する必要がある Compare() メソッドです。 Compare() は型 T の 2 つのオブジェクトを受け取り、整数を返します。メソッドのシグネチャは次のとおりです:
int compare(T o1, T o2);
このメソッドは、o1 が o2 より小さい場合は負の数を返し、それらが等しい場合はゼロを返し、o1 が o2 より大きい場合は正の数を返します。通常はそれぞれ -1、0、または 1 を返します。
オブジェクトの順序はこれに依存するため、compare() メソッドが返す内容を分析してみましょう。メソッドが返す内容の意味は相対的なものであること、つまり昇順または降順の順序を指定する場合に考慮することが重要です。それは状況とそれがどのように実装されるかによって異なります。それぞれの例について、次の レコード を考えてみましょう:
int[] numbers = {9, 8, 5, 3, 1, 2, 4, 6, 7}; Arrays.sort(numbers); System.out.println(Arrays.toString(numbers)); // Output [1, 2, 3, 4, 5, 6, 7, 8, 9]
int compare(T o1, T o2);
public record Movie( String name, List<String> actors, int budget, int year ) { } </p> <ul> <li>最初の引数が 2 番目の引数と等しい場合、ゼロが返されます。たとえば、映画を俳優の数で並べ替えるには、映画 a が映画 b と等しい場合に 0 を返すことができます。 </li> </ul> <div class="code" style="position:relative; padding:0px; margin:0px;"><pre class="brush:php;toolbar:false">// a < b -> -1 a.year() < b.year() -> -1
List
// a > b -> 1 a.budget() > b.budget() -> 1
映画をリリース年ごとに昇順に並べる場合は、Comparator
// a == b -> 0 a.actors().size() == b.actors().size() -> 0
sort() メソッド内の匿名クラスとして実装することもできます。
Movie movie1 = new Movie("The Godfather", Arrays.asList("Marlon Brando", "Al Pacino"), 6000000, 1972); Movie movie2 = new Movie("The Godfather: Part II", Arrays.asList("Al Pacino", "Robert De Niro"), 13000000, 1974); Movie movie3 = new Movie("The Shawshank Redemption", Arrays.asList("Tim Robbins", "Morgan Freeman"), 25000000, 1994); Movie movie4 = new Movie("The Dark Knight", Arrays.asList("Christian Bale", "Heath Ledger"), 185000000, 2008); List<Movie> movies = Arrays.asList(movie1, movie2, movie3, movie4);
より簡潔には、sort() メソッドでラムダ式を直接使用します。
Comparator<Movie> comparatorByYear = new Comparator<Movie>() { @Override public int compare(Movie o1, Movie o2) { return o1.year() - o2.year(); } }; movies.sort(comparatorByYear);
これらの実装はいずれも、リリース年の昇順でリストを並べ替えます。降順で並べ替える場合は、ラムダ式の引数の順序を変更するか、減算に負符号を追加します。
movies.sort(new Comparator<Movie>() { @Override public int compare(Movie o1, Movie o2) { return o1.year() - o2.year(); } });
カスタム オブジェクトのリストを並べ替える方法の他の例は次のとおりです。
movies.sort((p1, p2) -> p1.year() - p2.year());
movies.sort((p1, p2) -> p2.year() - p1.year()); // o movies.sort((p1, p2) -> - (p1.year() - p2.year()));
movies.sort((p1, p2) -> p1.actors().size() - p2.actors().size());
他の例としては、整数のリストを降順に並べ替える必要がある場合があります。
movies.sort((p1, p2) -> p2.budget() - p1.budget()); // o movies.sort((p1, p2) -> - (p1.budget() - p2.budget()));
これを行うには、要素を降順に並べるコンパレータを返す静的メソッド Comparator.reverseOrder() と、要素を昇順に並べる Comparator.naturalOrder() を使用することもできます。
int[] numbers = {9, 8, 5, 3, 1, 2, 4, 6, 7}; Arrays.sort(numbers); System.out.println(Arrays.toString(numbers)); // Output [1, 2, 3, 4, 5, 6, 7, 8, 9]
Java 内には、この種の比較を効率的な方法で実行できるメソッドがすでにあります。たとえば、2 つの整数を比較し、最初の引数が 2 番目の引数であるゼロより小さい場合に負の数を返す Integer.compare() などです。 if が等しい場合は、最初の引数が 2 番目の引数より大きい場合は正の数になります。このメソッドがどのように動作するかを分析すると、これが上で説明したものと似ており、Comparator インターフェイスの Compare() メソッドが必要とするものを正確に返すことがわかります。 Integer.compare() の実装は次のとおりです:
int compare(T o1, T o2);
映画を公開年ごとに昇順に並べ替えたい場合は、Integer.compare():
を使用できます。
public record Movie( String name, List<String> actors, int budget, int year ) { }
参照メソッドを使用して、以前とは異なる比較を実行することができます。たとえば、整数のリストを昇順で並べ替えることができます。
// a < b -> -1 a.year() < b.year() -> -1
Integer は、compareTo() メソッドを持つ唯一のクラスではありません。たとえば、String には、2 つの文字列を辞書順に比較する CompareTo() メソッドがあるため、文字列のリストを並べ替えたり、CharSequence を使用したりすることもできます。 Compare() メソッド (技術的には一連の文字を表します)。
// a > b -> 1 a.budget() > b.budget() -> 1
映画の例に戻ります。映画を公開年ごとに昇順に並べ替える場合は、comparingInt() メソッドを参照メソッドとして使用できます。
// a == b -> 0 a.actors().size() == b.actors().size() -> 0
または、文字列型属性 (この場合は映画の名前) に従って比較するには:
Movie movie1 = new Movie("The Godfather", Arrays.asList("Marlon Brando", "Al Pacino"), 6000000, 1972); Movie movie2 = new Movie("The Godfather: Part II", Arrays.asList("Al Pacino", "Robert De Niro"), 13000000, 1974); Movie movie3 = new Movie("The Shawshank Redemption", Arrays.asList("Tim Robbins", "Morgan Freeman"), 25000000, 1994); Movie movie4 = new Movie("The Dark Knight", Arrays.asList("Christian Bale", "Heath Ledger"), 185000000, 2008); List<Movie> movies = Arrays.asList(movie1, movie2, movie3, movie4);
場合によっては、オブジェクトのリストを複数の属性で並べ替える必要がある場合があります。たとえば、映画をリリース年ごとに昇順に並べ替え、予算ごとに降順に並べ替えたい場合は、次のメソッドを受け取る thenComparing() メソッドを使用できます。コンパレーターであり、複数の属性による順序付けを担当します。たとえば、公開年が同じ 2 つの映画 a と b がある場合、予算順に並べられます。
Comparator<Movie> comparatorByYear = new Comparator<Movie>() { @Override public int compare(Movie o1, Movie o2) { return o1.year() - o2.year(); } }; movies.sort(comparatorByYear);
コンパレータは、パーソナライズされた方法でオブジェクトを比較できるため、Java で多くの場面で役に立ちます。それだけでなく、多くの Java コレクション メソッドでも使用でき、並べ替えるための複数のコンパレータを使用することもできます。さまざまな方法で。いずれの場合でも、IDE 内の Comparator ドキュメントまたは公式 Java ドキュメントを参照して、使用できるメソッドとその実装方法を確認できます。
以上がComparator は Java でどのように機能しますか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。