android外部存储
⑴ Android各版本的外部存储配置建议
采用分区存储只能读写外部共享目录。
采用非分区存储是可以读写外部存储任何目录的。
注意:android10在分区存储模式下不能用文件路径读写外部共享文件,但在android11在分区存储下又可以用文件路径读写外部共享文件,所以如果您的项目存在通过文件路径来读写外部共享文件,要在配置文件中设置 android:requestLegacyExternalStorage="true" 来适配android10
结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
a 应用从非分区存储更新,结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
b 正常卸载安装 结果 Environment.isExternalStorageLegacy() 为 flase ,采用的是分区存储方法。
结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
结果 Environment.isExternalStorageLegacy() 为 false,采用的是分区存储方法。
a、应用从非分区存储更新,结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
b、应用正常卸载安装或者从分区存储更新,结果 Environment.isExternalStorageLegacy() 为 flase,采用的是分区存储方法。
结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
a 应用从非分区存储更新,结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
b 正常卸载安装 结果 Environment.isExternalStorageLegacy() 为 flase ,采用的是分区存储方法。
结果 Environment.isExternalStorageLegacy() 为 true,采用的是非分区存储方法。
采用的是非分区存储方法
⑵ Android外部存储ExternalStorage
内存(emory)
内部存储(ternalStorage)
1)storage或者mnt文件夹下
2) 通过:
Environment.getExternalStorageDirectory()
可以看到外部存储的位置
3) 公有目录(DCIM、DOWNLOAD等),要使用需要申请权限。
4) 私有目录(Android/data/应用包名),只能被当前应用访问。
String path= Environment.getExternalStorageDirectory().getAbsolutePath() +"/Mytest.txt";
try {
if (!file.exists()) {
file.createNewFile();
}
}catch (IOException e) {
e.printStackTrace();
}
try {
if (!file.exists()) {
file.createNewFile();
}
FileOutputStream fos=new FileOutputStream(path,true);
String str=infoEdt.getText().toString();
fos.write(str.getBytes());//以字节流的方式写入
}catch (IOException e) {
e.printStackTrace();
}
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>
其中第二条权限可能会报错,这时候解决办法是:
在报错的地方添加
tools:ignore="ProtectedPermissions"
同时在manifest标签里添加;
xmlns:tools="http://schemas.android.com/tools"
FileInputStream fis =new FileInputStream(path);
byte[] b =new byte[1024];
int len = fis.read(b);//读取fis字节流,将其存储在字节数组b中,并返回数组的长度(字节的个数)
String str2=new String(b,0,len);
txt.setText(str2);
注意:1、从外部存储读取文件不需要权限
2、Android6.0以上对外部存储(内存卡)共有目录的读写需要运行时权限(允许访问内存卡),这个权限需要用户手动开启,只在AndroidManifest.xml中申请是没用的。
int permissionContextCompet.checkSelfPermission(context,permission) 检查是否具有权限
第一个参数,环境上下文(this),第二个参数,权限名,Manifest.permission.WRITE_EXTERNAL_STORAGE,返回的是一个int类型的变量,将其与PackageManger.PERMISSION_GRANTED比较,等于则说明有权限,不等于的话则要动态申请权限:
if(permission!= PackageManager.PERMISSION_GRANTED){
//没有权限,则要申请权限
}
ActivityCompet.reaquestPermissions(activity,permission,code) 请求权限,第一个参数:activity 第二个参数:String类型的数组,里面装了各种权限, 当有多项权限需要申请的时候可以一起申请,第三个参数:一个int类型的请求码,动态申请权限的时候会触发onRequestPermissionsResult()方法,如果在申请的过程中有什么需要做的操作可以定义在该方法中,第三个参数请求吗可以帮助知道是那个权限的申请触发了这个方法
int permission=ContextCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE);
if(permission!= PackageManager.PERMISSION_GRANTED){
ActivityCompat.requestPermissions(this,new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},1);
}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if(requestCode==1){
//当前没有什么要处理的
}
}
通过:Environment.getExternalStorageDirectory()获取到的是根目录,通过在后面拼接目录名称,可以访问到公有目录
要获取外部存储目录的私有目录,可以通过:
1)Context.getExternalFilesDir(String type)获取到SDCard/Android/data/包名/files/目录,这个目录下一般存放一些需要长时间保存的数据。这个参数是用于指定文件夹类型的(图片,音乐,视频...)。
2)Context。getExternalCacheDir()获取到SDCard/Android/data/包名/cache/目录,这个目录下面一般存放一些临时的缓存性的数据。
⑶ xamarin怎样获取android外卡路径
xamarin怎样获取android外卡路径
一部分手机将eMMC存储挂载到 /mnt/external_sd 、/mnt/sdcard2 等节点,而将外置的SD卡挂载到 Environment.getExternalStorageDirectory()这个结点。
此时,调用Environment.getExternalStorageDirectory(),则返回外置的SD的路径。
android 怎样动态的获取sd卡路径
链接电脑USB调试情况下,在电脑上有新的磁盘显示,一个SD的,一个手机的,打开SD的就可以找各文件夹路径
Android怎样获取外部存储器路径
读写sdcard上的文件
其中读写步骤按如下进行:
1、调用Environment的getExternalStorageState()方法判断手机上是否插了sd卡,且应用程序具有读写SD卡的权限,如下代码将返回true
Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)
2、调用Environment.getExternalStorageDirectory()方法来获取外部存储器,也就是SD卡的目录,或者使用"/mnt/sdcard/"目录
3、使用IO流操作SD卡上的文件
注意点:手机应该已插入SD卡,对于模拟器而言,可通过mksdcard命令来创建虚拟存储卡
必须在AndroidManifest.xml上配置读写SD卡的权限
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
我怎样才能获得外部SD卡路径为Android 4.0 +
1. 我想你需要这个外部SD卡:
new File("/mnt/external_sd/")
或
new File("/mnt/extSdCard/")
你的情况......
在更换Environment.getExternalStorageDirectory()您的作品,应在MNT目录优先和工作在那里检查什么..
你键入选择哪个SD卡
File storageDir = new File("/mnt/");
if(storageDir.isDirectory()){
String[] dirList = storageDir.list();
TODO some type of selecton method?
}
怎样获取class路径
- importjava.io.File;
-
publicclassFileTest{
-
publicstaticvoidmain(String[]args)throwsException{
-
System.out.println(Thread.currentThread().getContextClassLoader()
-
.getResource(""));
-
System.out.println(FileTest.class.getClassLoader().getResource(""));
-
System.out.println(ClassLoader.getSystemResource(""));
-
System.out.println(FileTest.class.getResource(""));
-
System.out.println(FileTest.class.getResource("/"));
-
Class文件所在路径
-
System.out.println(newFile("/").getAbsolutePath());
-
System.out.println(System.getProperty("user.dir"));
-
System.out.println(System.getProperty("file.encoding"));
-
}
-
}
android 怎么获取相册路径
android手机4.2版本之前是一个方法,大于4.2版本又是一个方法。
注意:现在手机市场android版本2015面上半年平均4.4,现在是平均5.0了。
-
before
你网络一下,都能查到,很简单.
-
after
private void startPickPhotoActivity() {
Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT);
intent.setType("image/*"); Or 'image/ jpeg '
startActivityForResult(intent, RESULT_PICK_PHOTO_NORMAL);
}
获得图片返回的路径
@Override
protected void onActivityResult(int requestCode, int resultCode,
Intent data) {
if (requestCode == RESULT_PICK_PHOTO_NORMAL) {
if (resultCode == RESULT_OK && data != null) {
选中图片路径
mFileName = MainActivity.getPath(getApplicationContext(),
data.getData());
if ("".equals(mFileName)) {
return;
}
Intent intent = new Intent(this, EditActivity.class);
intent.putExtra("pathName", mFileName);
startActivity(intent);
}
}
}
@TargetApi(Build.VERSION_CODES.KITKAT)
public static String getPath(final Context context, final Uri uri) {
final boolean isKitKat = Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT;
DocumentProvider
if (isKitKat && DocumentsContract.isDocumentUri(context, uri)) {
ExternalStorageProvider
if (UriUtils.isExternalStorageDocument(uri)) {
final String docId = DocumentsContract.getDocumentId(uri);
final String[] split = docId.split(":");
final String type = split[0];
if ("primary".equalsIgnoreCase(type)) {
return Environment.getExternalStorageDirectory() + "/"
+ split[1];
}
}
DownloadsProvider
else if (UriUtils.isDownloadsDocument(uri)) {
final String id = DocumentsContract.getDocumentId(uri);
final Uri contentUri = ContentUris.withAppendedId(
Uri.parse("content:downloads/public_downloads"),
Long.valueOf(id));
return UriUtils.getDataColumn(context, contentUri, null, null);
}
MediaProvider
else if (UriUtils.isMediaDocument(uri)) {
final String docId = DocumentsContract.getDocumentId(uri);
final String[] split = docId.split(":");
final String type = split[0];
Uri contentUri = null;
if ("image".equals(type)) {
contentUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
} else if ("video".equals(type)) {
contentUri = MediaStore.Video.Media.EXTERNAL_CONTENT_URI;
} else if ("audio".equals(type)) {
contentUri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
}
final String selection = MediaColumns._ID + "=?";
final String[] selectionArgs = new String[] { split[1] };
return UriUtils.getDataColumn(context, contentUri, selection,
selectionArgs);
}
}
MediaStore (and general)
else if ("content".equalsIgnoreCase(uri.getScheme())) {
Return the remote address
if (UriUtils.isGooglePhotosUri(uri))
return uri.getLastPathSegment();
return UriUtils.getDataColumn(context, uri, null, null);
}
File
else if ("file".equalsIgnoreCase(uri.getScheme())) {
return uri.getPath();
}
return null;
}
如何获取android sdcard路径
Environment.getExternalStorageDirectory()
android怎么获取U盘路径
用Re管理器进入/mnt/目录一个一个找
android怎么获取分区路径
我们可以在adb中使用df 来查看分区情况。
1、跨分区不能用 MV命令来拷贝。但是可以用CP命令。如PWD,当前目录为:/data/local/tmp 。
此目录下有个busybox和1.txt文件。则利用CP命令拷贝如下:./busybox cp1.txt /system.
2、Android的用户组有 System, root, shell
3、怎么样才能操作分区。
分区操作是需要权限的。一般来说System分区的权限限制得比较严,Data分区限制比较严,用户可以操作的目录有local,app目录。比如/data/local/tmp.
data分区常用目录:app , system , data ,local,misc 其中system,local可以进入并使用ls等命令。data,app可以进入,但不能用ls命令。
data/data目录:存放的是所有APK程序数据的目录,每个APK对就一个自己的Data目录,就是在data/data/目录下,会产生一个跟Package一样的目录。如有一个APK,它的包名叫.test.hello则,在data/data/目录下会有一个.test.hello的目录,这个APK只能操作此目录,不能操作其它APK的目录.这个在LINUX下叫做用户进程只能操作自己的进程目录.
data/app目录:用户安装的APK放在这里。我们如果把APK放入这个文件夹下面的话,就算安装好了。这就叫静默安装。不用管APK文件里面的lib目录下的库文件,系统会自动帮我们放入调用库的。
data/system目录下面有packages.xml ,packages.list,appwidgets.xml, 等等一些记录手机安装的软件,Widget等信息。
data/misc目录:保存WIFI帐号,VPN设置信息等。如保存了一个WIFI连接帐号,则此目录下的WIFI目录下面可以查看到。
system分区常用目录: app , lib, xbin, bin , media,framework.
system/app目录:存放系统自带的APK。没有测试过是否将APK放入到System/app目录下,也是静默安装APK。?
system/lib目录:存放APK程序用到的库文件。
system/bin目录和system/xbin目录:存放的是shell命令。
system/framework目录:启用Android系统所用到框架,如一些jar文件。
4 Android下面的目录都是有权限的,要操作目录都需要有此权限才能操作,如果没有,则使用chomd777来修改.如果是分区根目录,如/data分区, /system分区.都没有权限,则需要重新挂载. 使用 mount -oremount XX
⑷ 安卓内外部存储完全解析 -- 别再弄混了
安卓开发离不开手机存储,然而大部分人对于安卓开发中的存储概念存在误区,内部外部SD卡傻傻分不清?
以下引用来自对 官方文档 的理解
呵呵呵,先别说话,然而重点来了(敲黑板),按照官方的说法,
内部存储是指系统的存储空间,没有root是访问不到的呦亲,比如sharedPreferenced或者database都是保存在这里面的。
外部存储,又分为 2 部分:
然而现实中,常常有同事把手机那个32G,64G存储叫做内部存储= =,宝宝好累,人家明明是 ExternalStorage !!
希望本篇能让大家对内外部存储有一个正确鲜明的认识
getFilesDir()
路径如下
文档 云:若想操作该路径,你需要一个输出流:
就像这样:
注: this 是 context 对象
在
路径下会看到新文件哦
如果你还想读取的话, 文档 云:你需要一个输入流:
Log如下
getCacheDir()
文档 云:
路径如下:
特别的,还有getDir() :
getDir("- -!.txt", Context.MODE_PRIVATE).getAbsolutePath()
路径如下:
app_是系统自己加上去的
内部存储就是系统的存储,没有root你是看不到的,内部存储最大特点就是可以用Context对象调用各个获取路径的方法。比如: context.fileList()
那就是
下的文件遍历。
而 deleteFile("ABC") 就是
删除下名为 ABC 的文件
</br></br></br>
操作外部存储你首先需要以下权限
当你申请了write权限,那么read权限默认也就通过啦
再判断状态:
if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState))
Environment.getExternalStorageDirectory()
这个路径根据手机厂家不同会有些许变化
直接传入 Environment 中的常量获取相应的路径,如下:
Environment.(Environment.DIRECTORY_ALARMS));
或者
Environment.(Environment.DIRECTORY_PICTURES));
公有目录下,系统会区分不同类别 (例如铃声在系统设置中显示为铃声而不是音乐)
4.4以后访问该目录不再需要权限了
getExternalFilesDir(String type)
eg.
getExternalFilesDir(Environment.DIRECTORY_MUSIC)
特别的:ContextCompat下的
ContextCompat.getExternalFilesDirs(context,type)
返回一个File[],在4.4以后第一条数据默认外部主存储目录,第二条数据就是sd卡路径啦,但是注意4.4之前是没有第二条数据的哦
该目录下的特点是卸载程序后,该目录和其下所有文件均会被删除
getExternalCacheDir()
注意,使用该目录注意管理空间,你不能等系统帮你清理,而是自己清理不再需要的缓存
特别的:ContextCompat下的
ContextCompat.getExternalCacheDirs()
道理同上
发现特点了吗朋友,无论外部内部,只有路径中有包名,那么就是私有的,而且是随着程序的卸载而被删除的, 有包名的路径均是Context中的方法,而公有的路径均是Environment调用的
这个货真真是要了老命,一般的方法根部不好使,结合网上有的方法加上公司项目中的方法,总结如下:
百分百好用的获取SD卡路径方法:
最后集合 path 中的值就是SD卡根目录
虽然无视版本百分百好用,但是如果你的手机有SD卡槽却没插SD卡,该方法最后 path 返回的是 null ,也就是说该方法无法判断到底是没插SD卡还是根本不支持SD卡
其实还有一种方法
String path = System.getenv("SECONDARY_STORAGE");
该方法只要你手机支持SD卡,无论你插没插SD卡,均会返回SD卡路径,但是 6.0及以上该方法被移除
Environment中源码其实就是根据这个方法获取路径的
安卓官方文档大家一定要看,他就是我们开发者的权威呀,圣经呀!!
⑸ Android 内部存储/外部存储 及 读写权限
Android 使用 VFS (Virtual File System) 虚拟文件系统。VFS提供了供存储设备挂载的节点,同一存储设备经过分区后,不同的分区可以挂载到不同的节点上,如手机的内置存储卡。
内置存储卡 / 外置SD卡
内部存储 / 外部存储
VFS 的目录以 / 为根节点,根节点下面又有不同的节点。物理存储设备就是挂载到这些节点上。
内部存储卡/外置SD卡 ≠ 内部存储/外部存储
首先明确, 内置存储卡/外置SD卡 是在 物理层面 相对于 手机大众用户 来说的。
外置SD卡:可手动插拔的SD卡。
内置存储卡:焊接在手机内部不可拆卸的存储卡。
而, 内部存 /外部存储 是在 文件系统逻辑层面 相对于 开发者 来说的,指具体的路径。
一般针对某个应用而言的,属于该应用的存储路径叫内部存储,反之为外部存储。
路径: /data/data/package_name
/data/data/ 下都是已安装应用的目录,该目录下包含的文件都是以包名作为文件名的目录,例如 /data/data/com.sankuai.meituan
获取内部存储的方式如下:
其中,参数 mode 指创建模式,一种 4 种
注意: Android 7.0 以上 android.os.Build.VERSION.SDK_INT>=Build.VERSION_CODES.N 使用3/4 常量时,将会导致SecurityException,这意味着 不能通过名称共享私有文件 。
尝试共享 file://URI URI将会导致FileUriExposedException,StrictMode API政策禁止在您的应用外部公开file://URL。如果您的应用需要与其他应用共享私有文件,则可以使用 FileProvider 与 FLAG_GRANT_READ_URI_PERMISSION 配合使用。 Android 7.0 行为变更 通过FileProvider在应用间共享文件吧
外部存储,可以是 外置SD卡 或 内置存储卡的部分分区。
外部存储,分为 公共目录 和 私有目录
获取方式
检查可用性的方法:
Android 4.3 以下,只能通过 Context#getExternalFilesDir(type) 来获取外部存储在内置存储卡分区的私有目录,无法获取外置SD卡。
Android 4.3 开始,可以通过 Context#getExternalFilesDirs(type) 获取一个File数组,包含了内置存储卡分区和外置SD的私有目录地址。
可以使用兼容库的静态方法 ContextCompate.getExternalFilesDirs() 兼容 4.3。
感谢以下文章作者
解析Android内部存储、外部存储的区别