背景
所有Android设备都有两个文件存储区域:内部存储和外部存储
尽管app默认安装在内部存储中,但可以在manifest文件中指定 android:installLocation 的属性,这样app便可安装在在外部存储中。当 APK 非常大且它们的外部存储空间大于内部存储时,用户更青睐这个选择。本篇文章针对的三星手机的目录,其他厂商的手机可能略有不同,请注意。
内部存储
- 它总是可用可访问的。
- 默认情况下只有你的应用可以访问此处保存的文件。
- 当用户卸载你的应用时,系统会从内部存储中删除您的应用的所有文件。
- 当您希望确保用户或其他应用均无法访问您的文件时,内部存储是最佳选择。
方法与路径:getFilesDir() (/data/data/com.zyou.test2/files)需要root
结果:此时手机未插入sdcard,可以看到内部存储的目录在根目录下的data/data/包名/
外部存储
- 它并非始终可用,因为用户可采用 USB 存储的形式装载外部存储,并在某些情况下会从设备中将其删除。
- 它是全局可读的,因此此处保存的文件可能被其他应用读取。
- 当用户卸载你的应用时,只有在你通过 getExternalFilesDir() 将你的应用的文件保存在目录中时,系统才会从此处删除您的应用的文件。
- 对于无需访问限制以及你希望与其他应用共享或允许用户使用电脑访问的文件,外部存储是最佳位置。
使用外部存储记得加上访问权限:
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
方法与路径:getExternalFilesDir("ff")(/storage/emulated/0/Android/data/com.zyou.test/files/ff)
结果:我们先来看看storage/emulated/0/ 原来这里就是外部存储目录,我们用手机自带的“我的文件”APP可以直接访问,并且我们发现许多常用的目录都在这里,比如Download Picture DCIM Documents Movies Music等。
其他存储区域
/storage/emulated/0
方法与路径:Environment.getExternalStorageDirectory() /storage/emulated/0
结果:这样子我们就能自由地访问外部存储/storage/emulated/0下的其他区域
<b>/storage/emulated/0/Download</b>
方法与路径:Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) /storage/emulated/0/Download
结果:这是公共存储区域,那么获取Picture,Documents,Music,Movies都是一样的方法;
<b>/system</b>
方法与路径:Environment.getRootDirectory() /system
结论:通过这个方法可以获取整个存储的顶级目录下的system目录,我觉得APP没有必要存储数据到这个地方了,最高存储地应该是/storage/emulated/0
<b>/data/app/com.zyou.test2-2/base.apk</b>
方法与路径:getPackageCodePath() /data/app/com.zyou.test2-2/base.apk
结论:返回android 安装包的完整路径,这个包是一个zip的压缩文件,它包括应用程序的代码和assets文件。
注意事项
1.在访问外部存储时,必须使用以下方法先判断外部存储是否存在。
if(Environment.getExternalStorageState().equals(Environment. MEDIA_MOUNTED)){ }
2.当您希望确保用户或其他应用均无法访问您的文件时,内部存储是最佳选择;对于无需访问限制以及你希望与其他应用共享或允许用户使用电脑访问的文件,外部存储是最佳位置。
3.访问权限设置
Context.MODE_PRIVATE = 0 : 为默认操作模式,代表该文件是私有数据,只能被应用本身访问,在该模式下,写入的内容会覆盖原文件的内容,如果想把新写入的内容追加到原文件中。可以使用Context.MODE_APPEND
Context.MODE_APPEND = 32768 :模式会检查文件是否存在,存在就往文件追加内容,否则就创建新文件。
Context.MODE_WORLD_READABLE = 1 :表示当前文件可以被其他应用读取;
Context.MODE_WORLD_WRITEABLE = 2 :表示当前文件可以被其他应用写入。
如果希望文件被其他应用读和写,可以传入: openFileOutput("itcast.txt", Context.MODE_WORLD_READABLE + Context.MODE_WORLD_WRITEABLE);