You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何优化Android中ContentResolver查询图片视频文件夹的速度

性能优化建议

以下优化点按收益从高到低排序,全部落地后9000个媒体文件的处理耗时预计可压缩到100ms以内:

1. MediaStore查询层优化(最大收益点)

  • 调整排序逻辑减少Cursor操作:当前你按DATE_ADDED正序查询,再调用moveToLast倒序遍历,完全可以直接修改排序语句为${MediaStore.Files.FileColumns.DATE_ADDED} DESC,直接正序遍历Cursor即可,避免Cursor倒走的额外开销。
  • 优化查询字段减少不必要的字符串操作:
    给projection新增MediaStore.Files.FileColumns.BUCKET_ID、MediaStore.Files.FileColumns.MEDIA_TYPE、MediaStore.Files.FileColumns.RELATIVE_PATH三个字段:
    • 用BUCKET_ID(Long类型)作为folderMap的key,替代当前你自己切割路径得到的字符串key,哈希映射查找效率提升50%以上,同时去掉path.substringBeforeLast("/")的字符串切割开销。
    • 用MEDIA_TYPE的Int值判断是否为视频,替代当前mimeType.contains("video")的字符串匹配操作,判断效率提升数倍。
    • 用RELATIVE_PATH判断是否为相机文件夹,替代path.contains(cameraPathName)的字符串匹配,同时适配Android 10+以上废弃DATA字段的规则。
  • 优化查询条件减少SQL解析开销:将当前硬拼接的selection改为占位符写法,系统解析SQL速度更快,同时避免注入风险:
    val selection = "${MediaStore.Files.FileColumns.MEDIA_TYPE} IN (?,?)"
    val selectionArgs = arrayOf(
        MediaStore.Files.FileColumns.MEDIA_TYPE_IMAGE.toString(),
        MediaStore.Files.FileColumns.MEDIA_TYPE_VIDEO.toString()
    )
    

2. 遍历逻辑优化

  • 删除冗余IO操作:当前你在bucketPath为空时创建File对象拿父路径,属于磁盘IO操作,新增BUCKET_ID和RELATIVE_PATH字段后不会出现bucketPath为空的情况,直接删除这段File创建逻辑即可,可减少大量IO开销。
  • 避免集合冗余拷贝:当前你先把所有媒体存入allMedias、allVideos,后续又调用allMedia.images.addAll(allMedias)做了一次全量元素拷贝,直接将allMedia.images引用指向allMedias即可,无需重复添加元素,省掉9000次元素插入开销。
  • 相机文件夹逻辑前置:遍历过程中识别到相机文件夹后单独存储,不要先存入folderMap再remove后插入列表头部,省掉一次Map的put和remove操作。

3. 集合操作优化

  • 预初始化集合容量:当前的allMedias、allVideos、folderMap都没有设置初始容量,ArrayList扩容时会触发多次数组拷贝,可提前查询媒体总数给allMedias设置初始容量,folderMap按设备平均相册数量设置初始值100,避免扩容开销。

4. 稳定性优化(无额外性能损耗)

将Cursor的关闭逻辑放到finally代码块中,避免异常时Cursor未关闭造成资源泄露。

内容的提问来源于stack exchange,提问作者Mohan K

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.18 18:36:03