2011-10-30 11 views
1

円形アレイの回転をより効率的にするにはどうすればよいですか?私は優秀なソートアルゴリズムについては、このthreadで読み、それが中央に並べ替えます、配列の末尾のスペースがあるので、私は必要なもののために動作しません。アレイの回転をより効率的にする方法はありますか?

回転機能は、左右回転の両方のために働く必要があります。アレイのすべてのスペースが満たされるわけではありません。

void Quack::rotate(int r) 
{ 
    if(r > 0) //if r is positive, rotate left 
    { 
     for(int i = 0; i < r; i++) 
      items[(qBack + i) % qCapacity] = items[(qFront + i) % qCapacity]; 
      //move items in array 
    } 
    else if(r < 0) //if r is negative, rotate right 
    { 
     for(int i = 0; i < (r * -1); i++) 
      items[(qFront - i - 1) % qCapacity] = 
       items[(qBack - i - 1) % qCapacity]; 
      //move items in array 
    } 
    //if r = 0, nothing happens 

    //rotate front and back by r 
    qFront = (qFront + r) % qCapacity; 
    qBack = (qBack + r) % qCapacity; 
} 
+3

ない、これは必ずしもあなたを助けます(あなたが解決しようとしている、より高いレベルの問題に依存します)が、あなたは可能性が開始オフセットを保持することによって、アレイ「回転」、およびちょうどあなたのアルゴリズムでループを調整していること。そのオフセットで読み込みを開始させ、最後まで読み込み、そのオフセットまで先頭から読み込みを続けます。 –

+0

回転の良いバージョンは、3つの反転として行われます:左のビットを反転させ、次に右のビットを反転し、次にアレイ全体を反転させます。しかしこれはより速いかもしれません。 –

答えて

1

私はそれを使用していないので、あなたが必要とするすべてを行うことはできません。しかし、単にこの関数本体をstd::rotate関数に置き換えることを検討したいかもしれません。

それはすでによく最適化されなければならない、とはるかに少ないアプリケーションにバグを導入する可能性が高くなります。

http://www.sgi.com/tech/stl/rotate.html

あなたがが最適化のための提案をしたい場合は、私はすべての剰余演算を避けることをお勧めします。彼らはあなたのプロセッサで実行できる最も高価な操作の1つである除算を必要とするかもしれません。彼らはあなたの目標を達成する方法を考えるのに便利な方法ですが、あなたのCPUが実行するには非常にコストがかかるかもしれません。最後に真ん中から1、そして真ん中に初めから他:あなたは二つのループを使用する場合

あなたは剰余演算子を削除することができます。

しかし、あなたは完全に回転を行うことを避けることができれば、あなたは、見ることができます。慎重であれば、無意味な完全配列トラバーサル/コピー操作を排除できる可能性があります。これを達成する方法については、OPに関するコメントを参照してください。

+0

これは正しく聞こえません。浮動小数点除算はかなり高価な演算ですが、整数除算(特にモジュラス)はかなり軽い計算です。 – TheBuzzSaw

+1

@ TheBuzzSaw:ループを正しく分割するのと比べて(プロセッサに何の費用もかからない)?いいえ、彼らは光ではありません。これが実際にアプリケーションのボトルネック(これを最適化する唯一の理由)であれば、これはまさに最適化のタイプです。 –

+0

私はモジュラス演算子のみを参照していました。私はそれを分解することは、それに関係なくより速いことに同意する。私は少し周りをグーグル。プロセッサは、モジュラス固有の最適化(特にARM)を備えています。心に留めておくだけのもの。 – TheBuzzSaw

関連する問題