6

のビット遷移の数を数える最速の方法を探していunsigned intます。

intに含まれる場合: 0b00000000000000000000000000001010

遷移の数は次のとおりです:4

intに含まれる場合: 0b00000000000000000000000000001001

遷移の数は次のとおりです:3

言語はCです。

4

6 に答える 6

17
int numTransitions(int a)
{
  int b = a >> 1; // sign-extending shift properly counts bits at the ends
  int c = a ^ b;  // xor marks bits that are not the same as their neighbors on the left
  return CountBits(c); // count number of set bits in c
}

CountBitsの効率的な実装については、 http ://graphics.stanford.edu/~seander/bithacks.html#CountBitsSetParallelを参照してください。

于 2009-01-23T09:31:07.250 に答える
2

最速はシナリオによって異なります。データ型を定数サイズ(unsigned int)として指定したため、ルックアップテーブルを使用できます。ただし、この操作が必要なのは、テーブルを初期化するための一定のオーバーヘッドが大きすぎる場合のみであり、intを介したスキャン+カウントはそれにもかかわらずはるかに高速です。

全体的に最適なのは組み合わせだと思います。テーブルでバイトまたはワードを検索し(256または64kエントリはそれほど多くありません)、バイト/ワードを最後/最初のビットで結合します。

于 2009-01-23T09:29:01.747 に答える
1

算術シフト + xor とカーニハンのビット カウント方法を使用したコードは次のとおりです。

int count_transitions(int x)
{
    assert((-1 >> 1) < 0); // check for arithmetic shift
    int count = 0;
    for(x ^= (x >> 1); x; x &= x - 1)
        ++count;
    return count;
}
于 2009-01-24T01:14:31.243 に答える
0

わかりました。トランジションでは、0-sと1-sの文字列をウォークスルーすると、0が1の後に続く、または1が0の後に続く各発生をカウントします。

これは、ビットをシフトアウトして変更をカウントすることで簡単になります。

transitions(n)
  result = 0
  prev = n mod 2
  n = n div 2
  while n<>0 
    if n mod 2 <> prev then
      result++
      prev = n mod 2
    fi
    n = n div 2
  elihw
  return result

modとdivをshiftsに置き換えることができます。

于 2009-01-23T09:24:25.250 に答える
0

何語?

私は64回ループし、次にビットをビットシフトしてビットを検査し、前のビットを保存して現在のビットと比較します。異なる場合は、カウントを増やしてください。

于 2009-01-23T09:20:57.143 に答える