我正在尝试为我们的服务器编写代码,我必须在其中通过 URL 查找用户访问类型。
现在,在一开始,我们看到每天有 1 亿个不同的 URL 被访问。现在,随着时间的推移,它每天有近 6 亿个不同的 URL。
对于 1 亿人,我们所做的如下:
1) 使用并行数组构建 HashMap,其键是 URL 的一部分(表示为 LONG),值是 URL 的另一部分(表示为 INT) - 键可以有多个值。
2) 然后搜索 HashMap 以查找 URL 访问了多少次。
现在,随着 HashTable 变大,我们所做的如下:
1)建立两个/三个单独的HashTable,并加载并存储它(在一般文件系统上)以查找URL访问了多少次。
现在,问题是,
1) 虽然 HashTable 性能相当不错,但代码在加载/存储 HashTable 时需要更多时间(我们使用文件通道,加载/存储 HashTable 需要 16-19 秒 - 2 亿条目 - 因为负载因子为 0.5)
我们想问的是:
1)任何评论如何解决这个问题?
2)如何减少加载/存储时间(我之前问过但似乎文件通道是最好的方法)?
3)存储一个大的HashTable(超过内存)并重复缓存它会是一个很好的解决方案吗?如果是这样,如何做到这一点(至少一些指针)。我们尝试使用
RandomAccessFile raf = new RandomAccessFile("array.dat", "rw");
IntBuffer map = raf.getChannel().map(FileChannel.MapMode.READ_WRITE, 0, 1 << 30).order(ByteOrder.nativeOrder()).asIntBuffer();
但是,提供比以前更差的性能。
谢谢。
注意:
1) 根据 Stack Overflow 之前的建议,我们使用一些 NoSQL DB,例如 TokyoCabinet,但根据我们的经验,自定义 HashTable 在 1 亿个键值对上的性能比它更好。
2) 无法为磁盘缓存预读数据,因为系统启动时,我们的应用程序将开始工作,而第二天系统启动时。
我们忘记提到的是:
1)由于我们的应用是项目的一部分,并且应用在一个小校园,所以我们假设访问的URL不超过8亿。所以,你可以认为 600/700 的数据值是固定的。
2)我们主要关心的是性能。
3)我们必须在本地运行我们的应用程序。