2

T []配列内の2つのアイテムを比較する方法を理解しようとしています。これが、私が持っているものです。

public static <T extends Comparable< ? super T>> T getLargest(T [] a, int low, 
               int high){
    if(low>high)
            throw new IllegalArgumentException();
    T[] arrCopy = (T[]) new Object[high-low];
    for(int i=low;i<high;i++){
        if(a[i].compareTo(a[i-1])>0)
            arrCopy[i]=a[i];
        else
            arrCopy[i]=a[i+1];
    }
    return arrCopy[0];
}

そして、私はエラーを受け取ります:Exception in thread "main" java.lang.ClassCastException: [Ljava.lang.Object; cannot be cast to [Ljava.lang.Comparable;

これを解決する方法について何かアイデアはありますか?

4

6 に答える 6

5

次のように配列を割り当てることができます。

@SuppressWarnings("unchecked")
T[] arrCopy = (T[]) Array.newInstance(a.getClass().getComponentType(), high-low);

チェックされていない警告が必要ですが、これは実際には安全なはずです。

ところで、配列内で最大の要素を見つけたい場合は、ここにワンライナーがあります:

public static <T extends Comparable<T>> T max(final T[] data) {
    return Collections.max(Arrays.asList(data));
}

完全な問題については、次の2つのうちの1つを使用できます(これらは同等です)。

public static <T extends Comparable<T>> T maxA(final T[] data,int from, int to) {
    return Collections.max(Arrays.asList(Arrays.copyOfRange(data, from, to)));
}
public static <T extends Comparable<T>> T maxB(final T[] data,int from, int to) {
    return Collections.max(Arrays.asList(data).subList(from, to));
}
于 2011-10-17T15:23:41.417 に答える
2

1つのオブジェクトだけを気にするのに、なぜまったく新しい配列を作成するのかわかりませんが、問題はジェネリックとは関係ありません。を書くことができないのと同じように、のようObject[]なより具体的なタイプにをキャストすることはできません。String[]String s = new Object()

最大値のみを気にするので、配列全体ではなく、1つの値(これまでに見られた最大値)のみを追跡する方がはるかに理にかなっています。

于 2011-10-17T15:17:48.480 に答える
2

ここでエラーが発生します:

T[] arrCopy = (T[]) new Object[high-low];

すべてのオブジェクトのマザーオブジェクト(java.lang.object)を、最小公分母としてjava.lang.comparableを持つものにキャストすることはできないため、例外がスローされます。オブジェクト(java.lang.objectのように)はjava.lang.comparableを実装しません。

特定の例では、Tの配列(または少なくともjava.lang.comparable)を作成する必要があります。

于 2011-10-17T15:18:39.883 に答える
2

Objectインスタンスの配列がインスタンスの配列としての扱いに適していると想定する理由はありませんComparableObject強制的ににキャストダウンします。Tこれは拡張されると予想されますがComparable、ここでは、チェックされていない割り当ては必要ありません。

代わりに、アレイをコピーしない実装を検討してください。

public static <T extends Comparable<? super T>>
T getLargest(T[] a, int first, int last)
{
  // Don't tolerate an empty range:
  if (first >= last)
    throw new IllegalArgumentException();
  // Eventually checked by subsequent use of array index operator:
  if (first < 0 || first >= a.length ||
      last < 0 || last >= a.length)
    throw new IndexOutOfBoundsException();

  T largest = a[first];
  while (++first != last)
  {
    final T candidate = a[first];
    if (candidate.compareTo(largest) > 0)
      largest = candidate;
  }
  return largest;
}

または、を使用して、を通過しCollections#max()た後に配列を後として表示します。ListArrays#asList()

于 2011-10-17T15:36:36.757 に答える
2

使用する:

public static <T extends Comparable<? super T>> T max(final T[] data, int fromIndex, 
               int toIndex) {
    return Collections.max(Arrays.asList(data).subList(fromIndex, toIndex));
}
于 2011-10-17T15:42:38.853 に答える
0

に変更new Object[high-low];するだけnew Comparable[high-low];です。ジェネリックは下限まで消去されるため、TはComparableまで消去されます。

于 2011-10-19T20:48:18.863 に答える