1

敵のいない重複排除システムでMurmurHash3を使用したいと思います。したがって、Murmurhash3はたとえばファイルをハッシュします。

しかし、私はそれを使用するのに問題があります。つまり、私は何か間違ったことをしています。

Murmurhash3_x86_128()(ソースコード)関数は4つのパラメーターを受け取ります。これは彼らが何であるかについての私の理解です:

キー-ハッシュにデータを入力

len-データ長

シード-シード

out-計算されたハッシュ値

コードのこの部分が原因で、実行時にセグメンテーション違反で失敗します。

    void MurmurHash3_x86_128 ( const void * key, const uint32_t len,
                               uint32_t seed, void * out )
    {
     const uint8_t * data = (const uint8_t*)key;
     const uint32_t nblocks = len / 16;
     ...

     const uint32_t * blocks = (const uint32_t *)(data + nblocks*16);

     for(i = -nblocks; i; i++)
     {
            uint32_t k1 = blocks[i*4];
            ...
     }
     ...
    }

したがって、データの長さが15バイトを超える場合(この場合)、このforループが実行されます。ただし、ブロックはデータ配列の最後を指し、その位置の後にメモリ位置へのアクセスを開始します。セグメンテーション違反について説明します。したがって、キーをデータ配列だけにすることはできません。

私の質問は:キーパラメータに何を入れるべきですか?


問題が解決しました

Mats Peterssonの回答の後、コードにバグがあることに気付きました。私はint(署名済み)である必要があり、署名なしでした。これが、ブロックにメモリ位置を追加し、減算しない理由です。

4

1 に答える 1

1

blocks計算中のブロックの最後の偶数倍の16バイトを指します。

i-nblocksで開始し、常にゼロ未満です(ループはゼロで終了します)。

したがって、64バイトのデータがあるとすると、ポインタはバイトblocksを指し、はになります。data + 64nblocks4

k1 = blocks[i*4];初めて取得するときは、i = -4インデックス-16を取得します。これに、を掛けたものsizeof(*blocks)、つまり4(ほとんどのアーキテクチャではint = 4バイト)です。したがって、取得-64=開始アドレスはdataです。

于 2013-01-27T20:40:15.017 に答える