80

次のコードで:

static void findSubsets (ArrayList<Integer> numbers, int amount, int index)
{
    ArrayList <Integer> numbersCopy = new ArrayList<Integer>(numbers.size());
    Collections.copy(numbersCopy, numbers);
}

エラーが発生します:

Exception in thread "main" java.lang.IndexOutOfBoundsException: Source does not fit in dest
        at java.util.Collections.copy(Collections.java:548)
        at backtracking2.Main.findSubsets(Main.java:61)

なんで?

4

6 に答える 6

99

容量はサイズと同じではありません。渡すサイズ パラメータは、そのサイズに十分なメモリを割り当てるだけです。実際には要素を定義しません。それは実際には一種のばかげた要件ですがCollections.copy、それでも要件の 1 つです。

Collections.copyJavaDocsの重要な部分:

宛先リストは、少なくともソース リストと同じ長さである必要があります。それより長い場合、宛先リストの残りの要素は影響を受けません。

問題を完全に回避するには、Listをのコンストラクターに渡してArrayListすべてをコピーする必要があります。List

于 2011-05-27T03:52:05.577 に答える
30

それは非常に良い質問であり、コレクション容量を設定しても、基になるオブジェクトが必ずしも割り当てられるとは限らないという事実にほぼ確実に関係しています。

ArrayList <Integer> numbersCopy = new ArrayList<Integer>(numbers);
于 2011-05-27T03:51:18.357 に答える
6

コンストラクターArrayList(Collection<? extends E> c)は、すべての要素をc新しく作成されたインスタンスにコピーするため、 にコピーnumbersされnumbersCopyます。それはnumbersCopy.addAll(numbers)また、あなたが本当に必要としているものと同じです。

配列のすべての要素を保持するのに十分な大きさCollection.copyの配列が必要であることは理にかなっています。同様の類推は、C 関数などです。destsourcememcpy

于 2011-05-27T04:03:07.837 に答える