c语言中内存地址的接近完美或完美散列

c语言中内存地址的接近完美或完美散列,c,perfect-hash,C,Perfect Hash,我有一个从0xc0003000到0xc04a0144的内存地址列表。列表中有许多间隙和

我有一个从0xc0003000到0xc04a0144的内存地址列表。列表中有许多间隙和<4096个条目。它在编译时是已知的,我想为它制作一个完美的哈希

然而,在网上查找perfect hashing给我提供的信息主要与哈希字符串有关,它们似乎翻译得不好

为了清楚起见,我希望能够在运行时获取内存地址,并快速检查它是否在哈希中。目前我使用的是二进制搜索,平均大约有8个循环来找到答案


你知道我应该叫什么树吗?

这是一个gperf程序示例。我在样本数据中包含一个NUL和一个换行符,以证明它们不会导致它失败

%{
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <inttypes.h>
#include <arpa/inet.h>
%}
%%
"\xc0\x01\x02\x03"
"\xc0\xff\xff\xff"
"\xc0\xff\x00\xff"
"\xc0\x0a\xff\xff"
%%
int main(int argc, const char **argv)
{
    int i;

    for(i=1;i<argc;++i) {
        uint32_t addr = ntohl(strtoul(argv[i], 0, 16));
        if(in_word_set((char *)&addr, 4))
            printf("0x%08"PRIx32" is in the list.\n", htonl(addr));
        else
            printf("0x%08"PRIx32" is not in the list.\n", htonl(addr));
    }
    return 0;
}

平衡树怎么样,比如B树或红黑树?我认为基数树是稀疏整数值搜索的最佳搜索树。你不能将地址本身作为4字节字符串使用吗?gperf支持处理非NUL终止的字符串:我有一个整数值列表,我想检查运行时生成的值是否在该列表中。我会看一个基数树,BITSET是C++,这是C海峡。我相信平衡树与二元搜索一样,可以提高性能,这正是我所希望的。
gperf
听起来正是您所需要的。它看起来更干净,运行速度更快,如果gperf真的被设计用于此目的,那么它对我所做的工作非常有效,比二进制搜索(10000000个循环)快大约40%。基数树最终大约等于二进制搜索,它稍微好一些。
gperf -l addrs.gperf > addrs.c
gcc addrs.c -o addrs
./addrs c0000000 c0010203 c0ffffff c00affff c0ff0aff c0ffff00 c0ff00ff