2012-01-30 3 views
1

なぜこのコードが間違っていますか?私は紙の上で、何が間違っていないことをトレースしているクイックソートのピボットとしての最初の要素

:クイックソートでは、私は、ピボットとして最初の要素を取り上げています。

private void QuickSort(ref int [] S ,int l,int h) 
    { 
     //partioning 
     int pivot_index = l; 
     int j = 0; 
     int temp = 0; 
     for(int i=l+1;i<=h;i++) 
      if (S[pivot_index] > S[i]) 
      { 
       j++; 
       temp = S[i]; 
       S[i] = S[j]; 
       S[j] = temp; 
      } 
     pivot_index = j; 
     temp = S[l]; 
     S[l] = S[j]; 
     S[j] = temp; 
     //end partioning 

     if (l < h && pivot_index>l && pivot_index<h) 
     { 
      QuickSort(ref S, l, pivot_index - 1); 
      QuickSort(ref S, pivot_index + 1, h); 
     } 
    } 

はここに私のメインです:

 int[] List = get_input(textBox1.Text, ref n); 
     // 
     QuickSort(ref List, 0, n-1); 
+5

なぜあなたは参照によって配列を渡していますか?配列はすでに参照型です。 –

+0

あなたの表記に感謝 – PasJ

+3

純粋なC#コードではありませんか?なぜC++タグですか? –

答えて

1

あなたの機能は明らかに、アレイ内の[l, h]範囲を並べ替えることになっている、まだいくつかの理由のためにあなたは、要素数jと要素番号iを交換しています。後者(j)は[l, h]の範囲外です(常に最初は0で、1,2,3などとなります)。これで何をしようとしていますか?なぜあなたのソート範囲から離れて、全く関係のない遠隔地にあなたの要素を交換していますか?

言い換えれば、これはでもリモートで私にソートアルゴリズムクイックソートスタイルのようには見えません。 jで説明できない操作は、実装が実際に何かをソートできない1つの理由です。

+0

良いこと、はい、設定する必要がありますj = l; – PasJ

+0

それでも、アルゴリズムはまだ間違っています。 'S [i]'は左から右へ、 'S [j] 'は右から左へと検索する必要があります。これには合計3つのループが必要です。 1つは「i」を検索し、もう1つは「j」を検索し、もう1つは検索スワッププロセスを囲む。詳細は私の答えを見てください。 –

+0

@Olivier Jacot-Descombes:アルゴリズムは「間違っている」わけではなく、そこに「必要」がありません。範囲の反対側から2つのインデックスをお互いに向かって移動させるテクニックは賢明で効率的ですが、具体的にそれを行う必要は絶対にありません。配列を分割する必要があります。それはここで唯一の "必須"です。このパーティショニングは完全に無関係です。 OPがやっていることは、完全に有効なアプローチです。それは非効率的であるかもしれませんが、それでも完全に有効です。厳密に言えば、「3の中央値」の有用性の実用的な証拠方法:あなたは、彼は中央値、 – AnT

0

あなたのアルゴリズムは間違っています。ピボット値int pivot = S[pivot_index];を取得します。

次に、スワップする2つの要素を決定します。したがって、左からピボット値以上の最初の要素を決定します。これはiとなります。その後、右からピボット値以下の最初の要素を決定します。これはjとなります。 ijスワップS[i]およびS[j]未満である限り、このプロセスを繰り返します。あなたは再帰的クイックソートを呼び出すことができる場合に見える、作るためにこれ以上のスワップがないだけ後

。ここでは、左部と右部の2つのチェックが必要です。


また、中央の要素をピボット要素として使用する方がよいことに注意してください。要素があらかじめソートされているかソート順にソートされている場合は、QuickSortのパフォーマンスが向上します。

int pivot = S[(l+h)/2]; 
+0

は3 +の中央値は、中央を取り上げるよりも大幅に高速であります事実上存在しない。 –

+0

@Mooingダックを選ぶ方法についての提案を作るつもりなら – AnT

+0

@AndreyT:中央からピッキングするのは平均から平均25%です。 3人の平均値は21%です。これは実際の平均値に20%近く近づき、深さが減少し、大きな影響を与える可能性があります。また、最悪のケースの深さも半分にします。そして、[私のテストでは](http://ideone.com/Nruol)より高速で、600桁以上の要素の比較を少なくしています。しかし、私はそれがより複雑で、(せいぜい)約8%しか速くないことは認めています。 –

関連する問題