web-dev-qa-db-ja.com

Javaコレクションが最大値のインデックスの関数を提供しないのはなぜですか?

私は多くのプロジェクトでCollections.max(list)を使用していますが、その最大要素のindexを見つけたい場合があります。私が書くすべてのプログラムで自分のためにこれを行う関数を書くのはばかげています。

Collections インターフェイスがCollections.maxIndex(list)を提供しないのはなぜですか?

5
Seth

コレクションには最大値を1つだけ含めることができますが、その値を表すitemが複数ある場合もあります。たとえば、_{1, 9, 2, 9, 0}_の最大値は_9_で、_[1]_と_[3]_の両方の要素で表されます。

すべてのコレクションがインデックスアクセスをサポートしているわけではないことに注意してください。例えば_Set<Integer>_には意味のある最大値を設定できますが、要素をインデックスでアクセスしても意味がありません。

メソッドをListに制限しても、不格好ではない最大値のインデックスを見つけるために1つのメソッドを思いつくのは少し難しいでしょう。インデックスのリストを返すこともできますが、その場合は値が失われ、一部のコレクションでは、たとえばリンクリスト、インデックスによる要素へのアクセスが遅い。 Javaにはタプルの簡単な構文がないため、.getValue()および.getIndices()を使用して特別なタイプのオブジェクトを返す必要があります。

しかし、そのような操作は標準ライブラリでサポートされるほど一般的ではないと思います。最大値の検索は文字通り3〜4行のコードであり、インデックスの追跡は別の1〜2行であり、間違って実行する余地はほとんどありません。頻繁に行う場合は、独自のユーティリティクラスに簡単に配置できます。

16
9000

Java 8 Streams API をご覧ください。

リンク: http://docs.Oracle.com/javase/8/docs/api/Java/util/stream/package-summary.html

(免責事項:以前に使用したことはありません)

ただし、maxIndexをすぐに使用できる実装はありません。これを可能にするには、誰かがJava 8ストリームの高性能プリミティブペアまたはタプルストリーム実装を提供する必要があります。

その理由はこれです。機能的に言​​えば、maxIndexは次のとおりです。

  • 次のように、各値をペア(2のタプル)に変換します:_(value, position)_
  • 次のようにストリームを減らします。
    • _(value1, position1)_と_(value2, position2)_の2つの項目を比較します。
    • より高い値のアイテムを保持し、その位置に沿ってコピーします。
      • つまり、return (item1.value > item2.value) ? item1 : item2;
    • 引き分けが可能な場合は、9000の回答で指摘されているように、引き分けのメカニズムも必要です。これはタプルを超える削減ではなくなりますが、「すべて同じ最大値を持つ(値、位置)タプルのコレクション」になります。
      • 同点のメカニズムが実装されている限り、ここで概説したアプローチは引き続き適用できます。
  • 操作の最後に、最大値として_item.value_を返し、最大インデックスとして_item.position_を返します。
    • 9000の回答で指摘されているように、タイブレークメカニズムによっては、複数の結果が生じる可能性があります。

残念ながら、多くのJava支持者が指摘したように、Javaは、クラスの幸福の爆発から経験している。これは、 Javaジェネリックサポート。その結果、Java APIで見つからないものが必要な場合は、独自のものをロールするか、ライブラリまたはツールボックスを見つける必要があります。します。

2
rwong