1、前言:
最近因为项目需要,需要对手机的文件进行分类浏览,获取手机中各种指定类型的文件。想到一年之前曾经用递归的方法列出手机的所有MP3文件,这个思路是很不错,但是这个方法对于层次不深的文件系统效果还勉强过得去,如果手机文件数量巨大,文件夹层次较深的文件系统而言,效率就特别低!有些甚至半分钟都扫描不完整个手机的文件。鉴于此,从开源的文件浏览器项目中得到启示,并和大家分享
2、正题:
Android系统给我们提供了android.provider.MediaStore.XXX类,里面有很多接口可以直接获取相应的文件,比如android.provider.MediaStore.Images用于获取所有格式的图片,android.provider.MediaStore.Audio用于获取所有格式的音频,今天要介绍的是作为通用接口的android.provider.MediaStore.Files类,通过它可以获取任何你指定类型的文件。
import android.content.ContentResolver;
import android.content.Context;
import android.database.Cursor;
import android.net.Uri;
import android.provider.MediaStore.Files;
import android.provider.MediaStore.Files.FileColumns;
import android.util.Log;
public class FileUtils {
public static void getSpecificTypeOfFile(Context context,String[] extension)
{
//从外存中获取
Uri fileUri=Files.getContentUri("external");
//筛选列,这里只筛选了:文件路径和不含后缀的文件名
String[] projection=new String[]{
FileColumns.DATA,FileColumns.TITLE
};
//构造筛选语句
String selection="";
for(int i=0;i<extension.length;i++)
{
if(i!=0)
{
selection=selection+" OR ";
}
selection=selection+FileColumns.DATA+" LIKE '%"+extension[i]+"'";
}
//按时间递增顺序对结果进行排序;待会从后往前移动游标就可实现时间递减
String sortOrder=FileColumns.DATE_MODIFIED;
//获取内容解析器对象
ContentResolver resolver=context.getContentResolver();
//获取游标
Cursor cursor=resolver.query(fileUri, projection, selection, null, sortOrder);
if(cursor==null)
return;
//游标从最后开始往前递减,以此实现时间递减顺序(最近访问的文件,优先显示)
if(cursor.moveToLast())
{
do{
//输出文件的完整路径
String data=cursor.getString(0);
Log.d("tag", data);
}while(cursor.moveToPrevious());
}
cursor.close();
}
上面是我写的一个文件工具类,都有注释,所以这里我就不再啰嗦了。调用时只需要传入context和后缀名就可
FileUtils.getSpecificTypeOfFile(this, new String[]{".doc",".apk"});
通过测试发现,用以前递归的方式,时间往往都是“秒级的”,而现在这个方法,基本上都是在“毫秒级”。效率提升了几十倍!
希望对大家有所帮助!