0

2 つの和 X=x1+x2+...+xn と Y=y1+y2+...+ym を考えてみましょう。xi を yj と交換すると 2 つの和が等しくなるようなインデックス i と j を見つけるアルゴリズムを与えてください。つまり、X-xi+yj = Y-yj+xi が存在する場合です。

こんにちは、みんな!そこに説明が表示されます。最初に、2 つのソートされていない配列を取得しています。それから私はそれらを並べ替えます。次に、それらの違いを見つけるためにそれらを互いに減算する必要があり、次に2つのforループで配列の要素の違いを比較します。

ここに私のコードがあります

Timport java.util.ArrayList;


public class algorithm {
int j;
int i;
int key;

public algorithm() {
    super();
    // TODO Auto-generated constructor stub
}

public ArrayList<Integer> sortingFunction(ArrayList<Integer> array){
    for(j=1;j<array.size();j++){
            key = array.get(j);
            i = j - 1;          
        while (i>=0 && array.get(i)>key){
            array.set(i+1, array.get(i));
            i = i - 1;  
        }
        array.set(i+1, key);
    }
    return array;
}


public int calculationFunction(ArrayList<Integer> array){
    int sum = 0;
    for(int x = 0; x<array.size(); x++){
        sum += array.get(x);
    }
        return sum;
}

public void writingFunction(ArrayList<Integer> array){
    for(int x = 0; x<array.size(); x++){
        System.out.print(array.get(x)+"  ");
    }
    System.out.println();
}

public void twoSumsEqualAlgorithm (int x, int y, ArrayList<Integer> array1, ArrayList<Integer> array2 ){
    int x_copy = x;
    int y_copy = y;
    //System.out.println(x);
    //System.out.println(y);
    for(int i = 0; i<array2.size(); i++){
        x_copy = x + (array2.get(i) * 2);
        //System.out.print("x;"+ x_copy);
        //System.out.println("  y;"+ y);
        if(x_copy >= y){
            for(int j = 0; j<array1.size(); j++){
                y_copy = y + (array1.get(j) * 2);
                if(x_copy == y_copy){
                    System.out.print("we have found the true values; ");
                    System.out.print("'"+array1.get(j)+"'"+" from myArray1("+j+ ") and ");
                    System.out.println("'"+array2.get(i)+"'"+" from myArray2("+i+")");
                    //return;
                }
                else if(x_copy < y_copy){
                    //System.out.println("x is lower than y");
                    break;
                }
            }
        }


    }

}

private void exit(int k) {
    // TODO Auto-generated method stub

}


}

これがテスト部分です

import java.util.ArrayList;


public class test {

/**
 * @param args
 */
public static void main(String[] args) {
     ArrayList<Integer> myArr1 = new ArrayList<Integer>();
     ArrayList<Integer> myArr2 = new ArrayList<Integer>();
     algorithm alg = new algorithm();

     myArr1.add(8);
     myArr1.add(4);
     myArr1.add(2);
     myArr1.add(15);
     myArr1.add(10);
     myArr1.add(16);
     myArr1.add(1);
     myArr1.add(11);


     myArr2.add(5);
     myArr2.add(3);
     myArr2.add(7);
     myArr2.add(6);
     myArr2.add(19);
     myArr2.add(2);
     myArr2.add(12);
     myArr2.add(1);
     myArr2.add(0);




     myArr1 = alg.sortingFunction(myArr1);
     myArr2 = alg.sortingFunction(myArr2);

     System.out.print("myArray1; ");
     alg.writingFunction(myArr1);
     System.out.print("myArray2; ");
     alg.writingFunction(myArr2);

     System.out.print("sum of myarray1; ");
     System.out.println(alg.calculationFunction(myArr1));
     System.out.print("sum of myarray2; ");
     System.out.println(alg.calculationFunction(myArr2));

     alg.twoSumsEqualAlgorithm(alg.calculationFunction(myArr1), alg.calculationFunction(myArr2), myArr1, myArr2);



}




}

したがって、アルゴリズムの複雑さを計算すると、O(n^2) になると思います。いくつかの投稿を読んだところ、O(nlgn) の複雑さで同じ仕事ができると書かれています。

2 つの配列リストを比較すると、big-O が低くなる方法で行うことができます。

マージソートまたはクイックソート O(nlg(n)) を使用して各配列リストをソートし、O(n) でソートされた 2 つのリストを比較できます。結果は O(nlgn) です。

しかし、別のアルゴリズム (並べ替えなし) は、1 つの配列 (n) 内の各要素を反復処理します。そして、要素が別の配列 (n) であるかどうかをチェックします (そして、重複を適切に処理するためにマークします)。この後者のアルゴリズムは O(n^2) です。

2 つのソートされた int 配列の比較

そのため、実装する方法がありませんでした。何か案は?

4

2 に答える 2

1

したがって、xi-yj == (XY)/2 を解く必要があります。

y 配列をソートし、x 配列をループします。x_i ごとに、(XY)/2-xi の y 配列でバイナリ検索を実行します。何かが止まっているのを見つけたら、そうでなければ続けます。ソートの複雑さは O(n log n) です。O(log n) の各ルックアップの複雑さと、最大で n 個のルックアップが必要です --> 合計の複雑さは O(n log n) です

于 2013-03-13T21:22:22.853 に答える
0

やりたいことは、2 つの配列の比較ではありません。設計は似ていますが、次のように解決するまったく異なるタスクです。

1) 両方のコレクションをマージソートまたはクイックソートします。適切に設計されている場合、これは O(nlgn) です。

2) コレクション x とコレクション y の数値を合計し、差 D.O(n) として XY を計算します。

3) (D が負であると仮定して) 最小から最大への x のスキャンと、最大から最小への y のスキャンを実行します。x のスキャンの各要素について、 x と y を交換すると D が PAST ゼロになるまで、y のスキャンの各要素をチェックします。これが発生した場合は、x を進め、y のスキャンで要素のチェックを続けます (たとえば、x のスキャンを進めるたびに y のスキャンをリセットしないでください)。

D がちょうど 0 になったら、スワップを見つけたことになります。x の要素を正確に 1 回読み取り、y の要素を最大で x.length+y.length 回読み取るため、これは最悪でも O(n) です。

4) (D が正であると仮定して) 上記と同様のロジックを実行しますが、x を最大から最小に、y を最小から最大にスキャンします。

于 2013-03-13T21:24:50.333 に答える