阅读:https://blog.csdn.net/f552126367/article/details/87873291
apk中有两种资源文件,raw下的和assert下的,这些数据只能读取,不能写入,两者目录下的文件在打包后会原封不动的保存在apk包中,不会被编译成二进制。res/raw中的文件会被映射到R.java文件中,访问的时候直接使用资源ID即R.id.filename;assets文件夹下的文件不会被映射到R.java中,访问的时候需要AssetManager类,res/raw不可以有目录结构,而assets则可以有目录结构,也就是assets目录下可以再建立文件夹
SD卡中的文件使用FileInputStream和FileOutputStream进行文件的操作。
存放在数据区(/data/data/…)的文件只能使用openFileOutput和openFileInput进行操作。注意这里不能使用FileInputStream和FileOutputStream进行文件的操作。
————————————————
存储介绍
Android系统分为内部存储和外部存储,内部存储是手机系统自带的存储,一般空间都比较小,外部存储一般是SD卡的存储,空间一般都比较大,但不一定可用或者剩余空间可能不足。一般我们存储内容都会放在外部存储空间里。使用过程注意事项:
- 先判断SD卡是否可用,可用时优先使用SD卡的存储,不可用时用内部存储
- 存储在SD卡上时,可以在SD卡上新建任意一个目录存放,也可以存放在应用程序内部文件夹,区别是在SD卡的任意目录存放时内容不会随应用程序的卸载而消失,而在应用程序内部的内容会随应用程序卸载消失。
- 一般缓存文件放在应用程序内部,用户主动保存的文件放在SD卡上的文件夹里。如果在SD卡上任意新建目录存放所有数据,用户卸载时会残存大量文件,招致用户反感。
存储路径
一般我们可以通过 Context 和 Environment 相关的方法获取文件存取的路径。
1.内部存储
1.1 根目录($rootDir
):/data
,通过 Environment.getDataDirectory()
获取。
1.2 应用程序目录($applicationDir
):$rootDir/data/包名
(不一定,不同设备可能不同)
应用缓存目录:$applicationDir/cache
,通过Context.getCacheDir()
获取。
应用文件目录:$applicationDir/files
,通过Context.getFilesDir()
获取。Context.getFileStreamPath(String name)
返回以name为文件名的子文件目录,若name为空,则返回文件根目录。假设我们的应用程序包名为com.learn.test,路径如下:
Environment.getDataDirectory(): /data
Context.getCacheDir(): /data/data/com.learn.test/cache
Context.getFilesDir(): /data/data/com.learn.test/files
Context.getFileStreamPath(""): /data/data/com.learn.test/files
Context.getFileStreamPath("test"): /data/data/com.learn.test/files/test
- 1
- 2
- 3
- 4
- 5
- 6
2.外部存储
2.1 根目录($rootDir
):/storage/emulated/0
(不一定,不同设备可能不同),通过 Environment.getExternalStorageDirectory()
获取。
2.2 应用程序目录($applicationDir
):$rootDir/Andorid/data/包名
应用缓存目录:$applicationDir/cache
,通过Context.getExternalCacheDir()
获取。
应用文件目录:$applicationDir/files
,通过Context.getExternalFilesDir(String type)
,type为空字符串时获取。type系统给我们提供了很多常用的类型,比如图片和下载等等:
public static String DIRECTORY_MUSIC = "Music";
public static String DIRECTORY_ALARMS = "Alarms";
public static String DIRECTORY_NOTIFICATIONS = "Notifications";
public static String DIRECTORY_PICTURES = "Pictures";
public static String DIRECTORY_MOVIES = "Movies";
public static String DIRECTORY_DOWNLOADS = "Download";
public static String DIRECTORY_DCIM = "DCIM";
public static String DIRECTORY_DOCUMENTS = "Documents";
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
假设我们的应用程序包名为com.learn.test,路径如下:
Environment.getExternalStorageDirectory(): /storage/emulated/0
Context.getExternalCacheDir(): /storage/emulated/0/Android/data/com.learn.test/cache
Context.getExternalFilesDir(""): /storage/emulated/0/Android/data/com.learn.test/files
Context.getExternalFilesDir("test"): /storage/emulated/0/Android/data/com.learn.test/files/test
Context.getExternalFilesDir(Environment.DIRECTORY_PICTURES): /storage/emulated/0/Android/data/com.learn.test/files/Pictures
- 1
- 2
- 3
- 4
- 5
2.3 公共存储目录: 我们可以在外部存储上新建任意文件夹,不过在6.0及之后的系统需要动态申请权限,这些目录的内容不会随着应用的卸载而消失。如:
Environment.getExternalStorageDirectory(): /storage/emulated/0
Environment.getExternalStoragePublicDirectory(""): /storage/emulated/0
Environment.getExternalStoragePublicDirectory("test"): /storage/emulated/0/test
Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES): /storage/emulated/0/Pictures
- 1
- 2
- 3
- 4
参考
转自:https://blog.csdn.net/nugongahou110/article/details/48154859
是时候弄清楚getExternalStorageDirectory()和getExternalFilesDir()的区别了
作为一个开发者,我们的确不应该将我们应用的数据直接存到SD卡的根目录下,当手机安装了大量的app时,SD卡根目录会迅速变得杂乱不堪。
这篇文章将带大家区分一下什么样的数据应该存放到什么样的路径下。
App专属文件 vs App独立文件
app专属文件就是那些只有该app才可以使用的文件,例如专属格式的电子书,app独立文件就是那些不依赖于某特定app的文件,例如照片。
App独立文件
这类文件当我们删除应用之后,还应该保留在手机上的,例如拍照的照片,不应该随着删除应用而被删除掉。对于这类文件,Android给我们提供了特定的目录,这些目录都是以DIRECTORY开头的,例如:DIRECTORY_MUSIC , DIRECTORY_PICTURES.
访问这些文件夹有两种方式:
第一种:
File sdCard = Environment.getExternalStorageDirectory();
- 1
这个sdCard的路径为mnt/sdcard/ 即为SD卡根路径,我们可以指定访问的文件夹名
File sdCard = Environment.getExternalStorageDirectory();
File directory_pictures = new File(sdCard, "Pictures");
Log.i(TAG,"directory_pictures="+directory_pictures);
- 1
- 2
- 3
- 4
得到的路径如下:
第二种:
File directory_pictures = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES);
Log.e(TAG, "directory_pictures="+directory_pictures);
- 1
- 2
得到的路径如下:
第二种方法是一个更加方便的访问Android给我们提供好的一些公共目录的方法,第一种方式更加灵活,可以自己指定目录。
App专属文件
这类文件应该是随着app删除而一起删除的,它们可以被存储在两个地方:internal storage 和 external storage 。 internal storage就是手机自带的一块存储区域,通常很小;external storage就是通常所说的SD卡,通常很大,有16GB,32GB等。
internal storage很小,所以你就应该很正确的使用它,因为SD卡有可能会被用户卸下,换成新的,所以SD卡不是任何时间都可用的,因此我们必须将一些重要的数据库文件以及一些用户配置文件存放在internal storage中。将一些大的图片或文件等缓存放到external storage中。
存储在internal storage
这是你app私有的目录,你的shared preference文件,数据库文件,都存储在这里。目录为data/data/< package name >/files/
访问方法为:
File filesDir = getFilesDir();
Log.i(TAG,"file_dir="+filesDir);
- 1
- 2
存储在external storage
这类文件不应该存在SD卡的根目录下,而应该存在mnt/sdcard/Android/data/< package name >/files/…这个目录下。这类文件应该随着App的删除而一起删除。例如一种格式的电子书,只有该app才可以打开,如果用户删除了该app,那么留下来的电子书就成为了一种无法打开的垃圾文件,所以应该随着该app一起删除掉。
获得这个路径的方法:
File externalFilesDir = getExternalFilesDir(null);
Log.i(TAG, "externalFileDir = "+externalFilesDir);
- 1
- 2
我们看一下log中的内容为null,这是由于我们没有添加权限
添加权限:
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
- 1
- 2
再看一下log:
这样路径就访问到了,我们注意到上面的getExternalFilesDir(null)参数传入的为null,这样默认访问的是files文件夹,我们可以指定子文件夹
File externalFilesDir = getExternalFilesDir("Caches");
Log.i(TAG, "externalFileDir = "+externalFilesDir);
- 1
- 2
有些时候我们的手机没有安装SD卡,所以我们使用前需要判断一下:
if(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
//SD卡已装入
}
- 1
- 2
- 3