2

2 つの文字列配列の結合を見つけようとしています。新しい配列を作成し、すべてのデータを最初のセットから新しい配列にコピーしました。2 番目のセットの情報を新しい配列に追加する際に問題が発生しています。

ループを使用して 2 番目の配列を検索し、重複を見つける必要があります。私は取得し続けArrayIndexOutOfBoundsExceptionます。

これが私の現在のコードです:

static String[] union(String[] set1, String[] set2) {
    String union[] = new String[set1.length + set2.length];

    int i = 0;
    int cnt = 0;

    for (int n = 0; n < set1.length; n++) {
        union[i] = set1[i];
        i++;
        cnt++;
    }

    for (int m = 0; m < set2.length; m++) {
        for (int p = 0; p < union.length; p++) {
            if (set2[m] != union[p]) {
                union[i] = set2[m];
                i++;
            }
        }
    }
    cnt++;

    union = downSize(union, cnt);

    return union;
}
4

5 に答える 5

8

交差または結合を行う標準的な方法は、セットを使用することです。Setコレクション フレームワークのクラスを使用する必要があります。

2 つの配列に対して 2 つの arraylist オブジェクトを作成します。
セット オブジェクトを定義します。
両方の arraylist オブジェクトを Set usingaddAll メソッドに追加します。

セットは一意の要素を保持するため、セットは両方の配列の和集合を形成します。

  //push the arrays in the list.
  List<String> list1 = new ArrayList<String>(Arrays.asList(stringArray1));
  List<String> list2 = new ArrayList<String>(Arrays.asList(stringArray2));

  HashSet <String> set = new HashSet <String>();

  //add the lists in the set.
  set.addAll(list1);
  set.addAll(list2);

  //convert it back to array.
  String[] unionArray = set.toArray(new String[0]);       
于 2013-10-16T03:49:10.700 に答える
4

を使用Setするのが最も簡単な方法の 1 つです。

public static String[] unionOf(String[] strArr1, String[] strArr2) {
    Set<String> result = new HashSet<String>();
    result.addAll(Arrays.asList(strArr1));
    result.addAll(Arrays.asList(strArr2));
    return result.toArray(new String[result.size()]);
}

Guava など、同様の作業に役立つ他のユーティリティもあります。

public static String[] unionOf(String[] strArr1, String[] strArr2) {
    return Sets.union(Sets.newHashSet(strArr1), 
                      Sets.newHashSet(strArr2))
               .toArray(new String[0]);
}
于 2013-10-16T04:04:53.680 に答える
3

コードのこの部分にはいくつかの問題があります。

for(int m = 0; m < set2.length; m++)
        for(int p = 0; p < union.length; p++)
            if(set2[m] != union[p])
            {   
                union[i] = set2[m];
                i++;        
            }
        cnt++;

まず、文字列を比較する!equals()代わりに使用する必要があります。!=第二に、インデントにもかかわらず、ステートメントcnt++は外側のループの一部ではありません。icnt;の両方は必要ありません。それらの値は常に一致する必要があります。最後に、それとは異なるset2[m]の要素ごとに 1 回追加します。union一度だけ追加します。動作するはずのバージョンは次のとおりです。

static String[] union( String[] set1, String[] set2 )
{
    String union[] = new String[set1.length + set2.length];
    System.arraycopy(set1, 0, union, 0, set1.length); // faster than a loop
    int cnt = set1.length;
    for(int m = 0; m < set2.length; m++) {
        boolean found = false;
        for(int p = 0; p < union.length && !found; p++) {
            found = set2[m].equals(union[p]);
        }
        if(!found)
        {   
            union[cnt] = set2[m];
            cnt++;        
        }
    }
    union = downSize( union, cnt );
    return union;
}

他の投稿者が指摘しているように、代わりのアプローチは a を使用HashSet<String>し、2 つの配列で見つかった要素を追加し、結果を配列に戻すことです。

于 2013-10-16T03:57:56.820 に答える
0

次の行で ArrayIndexOutOfBoundsException を取得します。

union[i] = set2[m];

iどこかで増加し続けるからです:set2.length * union.length時間(ネストされたループ)。

RJ が書いたことを実行してもユニオンは得られません - set2[m].equals(union[p])set2 のすべてのメンバーをユニオンのすべてのメンバーと比較し、それが等しくないメンバーごとに追加するため、重複するアイテムが多くなります。そのため、同じアイテムを複数回追加することになります!

それを行う正しい方法は、Deepak Mishra がSet重複の「世話をする」を使用して提案したようなものです。

例:

int[] a = {1,2,3,4,5};
int[] b = {4,5,6,7};
Set union = new HashSet<Integer>();
for(int i=0; i<a.length; i++) union.add(a[i]);
for(int i=0; i<b.length; i++) union.add(b[i]);
Object[] ans = union.toArray();
for(int i=0; i<ans.length; i++)
    System.out.print(ans[i]+" ");

出力します:

1 2 3 4 5 6 7 

それはHWなので、答えのコードは書きませんが、ヒントを提供します
。あなたのやり方でそれを行うには必要O(n^2)です-少し考えれば、でそれを行う方法を見つけることができると確信していますより良い時間、たとえば
O(n log n)...

于 2013-10-16T03:50:52.080 に答える
0

SETS を使用するのが最善の解決策ですが、ここでは簡単な解決策を示します。

 private static String getUnion(String a, String b, boolean ignoreCase) {

    String union = "";

    if (a == null || b == null || a.length() < 1 || b.length() < 1) {
        return union;
    }

    char[] shortest;
    char[] longest;

    if (ignoreCase) {
        shortest = (a.length() <= b.length() ? a : b).toLowerCase().toCharArray();
        longest = (a.length() <= b.length() ? b : a).toLowerCase().toCharArray();
    } else {
        shortest = (a.length() <= b.length() ? a : b).toLowerCase().toCharArray();
        longest = (a.length() <= b.length() ? b : a).toLowerCase().toCharArray();
    }

    StringBuilder sb = new StringBuilder();

    for (char c : shortest) {
        for (int i = 0; i < longest.length; i++) {
            if (longest[i] == c) {
                sb.append(c);
            }
        }
    }

    union = sb.toString();

    return union;
}

以下はいくつかのテストです。

public static void main(String[] args) {

    System.out.println("Union of '' and BXYZA is " + getUnion("", "BXYZA", true));
    System.out.println("Union of null and BXYZA is " + getUnion(null, "BXYZA", true));

    System.out.println("Union of ABC and BXYZA is " + getUnion("ABC", "BXYZA", true));
    System.out.println("Union of ABC and BXYZA is " + getUnion("ABC", "bXYZA", false));

}
于 2016-06-14T13:25:49.930 に答える