记Android外置存储区的坑

原创 2015年11月18日 01:55:12
一般情况下,Android应用会在外置存储区存储一些特别的数据,比如音乐类应用需要存储用户听过的歌的缓存或者下载的歌曲。通常情况下我们是直接通过
Environment.getExternalStorageDirectory()

这个方法来获取系统的外置存储区的,但是Android4.4以后,谷歌为了规范应用,防止应用在卸载后留下一大堆乱七八糟的文件夹在用户的外置存储区,所以非系统应用是无法直接操作该区域的,我们只能通过调用

getExternalFilesDir("yourfile");
这个方法在/.../外置存储区/Android/data/[应用包名]/路径下读写 写文件。这样做的好处是系统在卸载的时候会一并删除这块区域,保证外置存储区域的干净。不过许多厂商似乎都不太遵守这个规定,还是会把外置存储区的读写权限开放给所有应用,大部分的app也不遵守这个规定。个人觉得如果没有特别的需要 还是使用第二个api接口吧,还用户一个干净的存储空间。

说到这个外置存储区呢,我个人的理解是这样的,打开Android系统的根目录,一般会看见有一个sdcard的文件夹,这个文件夹所在的区域就是外置存储区域。一般情况下,Android设备都会分配一定空间给这个区域,即使你没有插入U盘之类的东西。以个人理解来看,这个叫sdcard的文件夹其实是一个快捷方式(以Windows的理解),实际上设备的存储区域是没有这块东西的,就像你把Windows电脑的D盘某个文件夹在桌面创建了一个快捷方式,你虽然可以通过这个快捷方式直接访问这个文件夹,但是实际上他并不在桌面这个路径下面。sdcard真正的路径应该是/storage/sdcard0/ ,当然也可能是sdcard1 2 3 或者其他名字。

前面提到一般情况下,Android设备是有sdcard这么一个分区的,无论有没有接入外接存储。但是有些设备就是不愿意给你划分这么一块区域,今天写文章就是因为遇到了这么一个设备。因为我的app需要往外置存储区域下载写入一些文件,所以在这个默认没有外置存储区域的设备上就报错了。一开始,我以为是Android系统不让我在外置存储区域写文件,必须写到指定地方才行,于是我把接口改成了

getExternalFilesDir("yourfile");
,但是这样还是报错,日志显示这个方法返回的是一个null的File对象。后来和设备厂商的技术人员沟通的时候,他们才告诉我他们没有为设备划分sdcard的分区,只有用户插入了U盘之类的才会有这个分区。其实这个异常信息我应该可以一开始就了解到的,但是因为在写代码的时候偷了一点懒,没有对sdcard分区状态进行判断,所以最后还是在和厂商沟通的时候才发现了异常信息。这一点也提示我代码健壮性的必要。

那么如何解决这个问题呢? 其实这个也比较简单,就是把文件写入到我们应用的安装目录下面,即:/data/data/[包名]/。但是这里面的文件仅限于该应用可读可写,因此我们需要对这个目录下我们手动创建的每一个文件夹以及每一个文件进行权限属性修改。我这里比较粗暴,直接chmod 777  文件名 。这样的话,其他应用也能够访问我们这些写入的数据了。


版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

c语言程序存储区的划分

内存区划分 从低到高  代码区 常量区 静态区  堆区  栈区 //栈内存是系统自动开辟,自动回收的存储区域,分配原则为:从栈内存的高位分配,再从已经分配的存储区域的低位开始存取数据,...

内存空间分配 堆、栈、静态存储区的区别

堆和栈的区别 一、预备知识—程序的内存分配 一个由c/C++编译的程序占用的内存分为以下几个部分 1、栈区(stack)— 由编译器自动分配释放 ,存放函数的参数值,局部变量的值等。其操作方式类...

静态存储区、栈区、堆区的区别

内存分配有三种:静态存储区、堆区和栈区。他们的功能不同,对他们使用方式也就不同。 静态存储区:内存在程序编译的时候就已经分配好,这块内存在程序的整个运行期间都存在。它主要存放静态数据、全局数...

SQL Server中TempDB管理(版本存储区的一个example)

原文来自: http://blogs.msdn.com/b/sqlserverstorageengine/archive/tags/tempdb/ http://blogs.msdn.com/b/...

C语言中存储区的划分

转载自http://smllys.blog.sohu.com/158991520.html 在c语言中,存储区可以分成代码区,全局区,常量区,栈,堆;如下图所示:        全局区 :主...

java中存储区的分类

Java中把存储区分为6类。分别为寄存器(register)、栈(stack)、堆(heap)、静态存储区(static storage)、常量存储区(constant storage)以及非随机存取...

【转】对内存中堆、栈、静态存储区的理解

堆:由程序员自己分配释放(用malloc和free,或new和delete) ,如果我们不手动释放,那就要到程序结束才释放。如果对分配的空间在不用的时候不释放而一味的分配,那么可能会引起内存泄漏,其容...

自由口通信模式下计算机读写PLC存储区的程序

自由口通信模式下计算机读写PLC存储区的程序 2008-8-20 8:51:00 来源: 摘 要:本文介绍了在自由口通信模式下,用计算机读写S7-200 PLC存储区内相邻...

Android判断是否存在外置SD卡(获取手机所有存储设备的路径)

public class StorageUtils { /* 获取手机里所有存储设备盘符,首先需要得到挂载在手机上的有哪些盘符,这里需要用到一个被系统隐藏的方法, 即Stor...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:深度学习:神经网络中的前向传播和反向传播算法推导
举报原因:
原因补充:

(最多只允许输入30个字)