图片数量增加时LMDB读取速度变慢的原因咨询
问题描述
我通过以下命令在Python环境中安装LMDB:
python -m pip install lmdb
随后将图片写入LMDB,设置两种存储场景:
- 存入6800张1024x2048尺寸的PNG格式图片
- 存入10000张同规格的PNG格式图片
我的内存容量为1T,读取LMDB的部分代码如下:
def init_lmdb(self): self.env = lmdb.open( self.file_root, map_size=2**40, readonly=True, max_readers=512, readahead=False, ) def get_bins(self, inds): im_bins = [] with self.env.begin(write=False) as txn: for ind in inds: impth = self.im_paths[ind] im_bin = txn.get(impth) im_bins.append(np.frombuffer(im_bin, dtype=np.uint8)) return im_bins
使用完全相同的代码读取这两个LMDB文件时,出现明显速度差异:
- 存储6800张图片的LMDB:随机顺序累计读取6400次(仅从其中3400张图片读取,可重复)耗时约9秒
- 存储10000张图片的LMDB:同样累计读取6400次(仅从其中5000张图片读取,可重复)耗时约16秒
请问造成这种读取速度差异的原因是什么?
原因分析
- 页缓存命中率差异:LMDB基于内存映射文件,依赖操作系统页缓存。尽管你有1T内存,但10000张图片的总数据量更大,仅读取其中5000张时,操作系统可能无法将这部分数据完全缓存到内存,部分读取需要从磁盘加载;而6800张场景中,3400张图片的总数据量更小,更容易被完全缓存,读取时大多命中内存,速度更快。
- 哈希表冲突与查找开销:LMDB内部用哈希表存储键值对,键的数量越多(10000 vs 6800),哈希冲突概率越高,每次
txn.get(impth)的查找耗时增加。随机读取场景下,冲突带来的额外查找操作会累积成明显时间差。 - 数据分布的连续性:写入LMDB时,键的顺序会影响数据在磁盘上的存储连续性。10000张图片的键分布可能更分散,对应的磁盘块也更分散,随机读取时磁盘寻道次数更多;6800张场景的数据分布更集中,寻道开销更小。即使内存充足,首次读取未缓存数据时,寻道差异直接影响速度,后续重复读取若未完全缓存,差异依然存在。
- 内存映射页的负载差异:LMDB的内存映射页大小由操作系统决定(通常4KB或更大)。10000张图片整体占用的页数量更多,读取时需要加载的页数量增加,间接拉高总耗时。
内容的提问来源于stack exchange,提问作者coin cheung
相关产品推荐
相关产品推荐

