题目
描述
现有数据如下:
K1-1-A-X0001=/common/gom/r00/xml/gom0101.xml
K3-2-B-W4565=/common/gom/r00/xml/gom0404.xml
K4-1-B-K0090=/common/gom/r00/xml/gom0403.xml
K2-3-A-W0004=/common/gom/r00/xml/gom0103.xml
...
...
其中第一列是ID,不重复;第二列是地址。数据供10万条。
请设计数据结构和算法,提供查询服务。比如:输入K4-1-B-K0090得到对应的地址/common/gom/r00/xml/gom0403.xml。
目标
查询最快、占用内存最少。
要求
不使用关系型数据库;使用文件系统进行存储;编程语言不限。
方案及代码
我把所有的代码放在了Github上:
https://github.com/longjingjun/Programming_Challenge_Query
使用Eclipse打开此项目。
方案1
使用Java里的Property文件存储数据,使用Java里的Properties类读取数据。
- FileBuilder.java:用来生成10万条数据
- Finder.java:查询代码实现
方案2
使用Mongo DB存储数据,然后使用Mongo DB的接口查询。
- MongoDBBuilder.java:用来向MongoDB插入10万条数据
- MongoDBFinder.java:查询代码实现。
注:运行此代码需要安装Mongo DB。请从这里下载安装包:
方案3
使用随机文件,第一行放数据的总数,后边按照从小到大的顺序存储数据。查询是使用折半查找算法进行查询。
- RamdomFileBuilder.java:按照设计生成10万条数据并保存到文件中。
- RamdomFinder.java:查询代码实现。
方案4
使用B-Tree,实现查询。这种方案我手头没有代码。
测试和结论
10万条数据,前三种方法的测试结果如下:
实现方案 | 测试轮 | 测试结果 (毫秒) |
||||||||
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | |||
normal prop - 1 |
1 | 274 | 265 | 248 | 289 | 295 | 265 | 278 | 218 | |
2 | 273 | 275 | 270 | 273 | 265 | 286 | 280 | 210 | ||
3 | 265 | 262 | 292 | 270 | 274 | 280 | 247 | 203 | ||
normal prop - 2 |
1 | 133 | 136 | 135 | 132 | 133 | 139 | 156 | 138 | |
2 | 145 | 148 | 136 | 135 | 141 | 134 | 135 | 137 | ||
3 | 134 | 136 | 136 | 139 | 129 | 142 | 143 | 139 | ||
MongoDB | 1 | 122 | 随着数据增多,查询的时间随着增长。 | |||||||
2 | 127 | |||||||||
3 | 115 | |||||||||
Random File | 1 | 1 | ||||||||
2 | 2 | |||||||||
3 | 1 |
专门针对B-Tree实现和随机文件方案进行了另一轮的测试,测试数据为100万条。测试结果如下:
100 万条数据 | ||||
1 | 4 | 7 | 10 | |
B-Tree | 121 | 31 | 93 | 53 |
125 | 29 | 105 | 52 | |
119 | 30 | 96 | 49 | |
随机文件 | 1 | 3 | 2 | 2 |
2 | 2 | 2 | 1 | |
1 | 2 | 2 | 1 |
根据测试结果,最快的方案是使用随机文件。同时这种方案有一个限制:每一行存储的数据是定长的,如何合理地设计每一行数据大小是一个很重要的问题。