• Android开发笔记(二十二)——数据存储之文件存储


    文件存储是利用Java的I/O流来实现向Android硬件磁盘上进行读写的操作。

    Android存储概念

    内部存储 Internal Storage :不可更改的,随着应用的卸载被删除

    内部存储的特点:

    • 默认只能被创建它的应用访问到
    • 当这个应用卸载后,内部存储中的文件也被删除
    • 一旦内部存储空间耗尽,手机也就无法使用

    /data/data/<applicationId>/shard_prefs

    /data/data/<applicationId>/databases

    /data/data/<applicationId>/files

    /data/data/<applicationId>/cache

    这四个文件夹都是属于内部存储。

    前两个文件是通过系统提供的类和方法来获得文件的内容。

    后两个文件是通过 context.getCacheDir()context.getFilesDir() 这两个方法来得到。

    外部存储 External Storage :可更改的。分为公有目录和私有目录,

    公有目录:通过 Environment.getExternalStoragePublicDirectory(int type) 方法来获得公有目录下对应类型的文件。

    私有目录:随着应用的卸载被删除
    /mnt/sdcard/data/data/<applicationId>/files

    /mnt/sdcard/data/data/<applicationId>/cache

    File内部存储

    比较重要的两个类: FileOutputStreamFileInputStream

    代码示例
    FileActivity的java文件:

    public class FileActivity extends AppCompatActivity {
    
        private EditText mEtName;
        private Button mBtnSave,mBtnShow;
        private TextView mTvContent;
    
        private final String mFinalName = "text.txt";
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_file);
    
            mEtName=findViewById(R.id.et_name);
            mBtnSave=findViewById(R.id.btn_save);
            mBtnShow=findViewById(R.id.btn_show);
            mTvContent=findViewById(R.id.tv_content);
    
    
    
            mBtnSave.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    save(mEtName.getText().toString().trim()); //trim()表示去除前后空格,没有也可以
                }
            });
    
            mBtnShow.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    mTvContent.setText(read());
                }
            });
        }
    
        //存储数据
        private void save(String content){
            FileOutputStream fileOutputStream=null;
            try {
                //创建存储目标
                fileOutputStream = openFileOutput(mFinalName,MODE_PRIVATE);
                //字节方式存储方法
                fileOutputStream.write(content.getBytes());
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                //关闭流
                if (fileOutputStream!=null) {
                    try {
                        fileOutputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        }
    
        //读取数据
        private String read(){
            FileInputStream fileInputStream = null;
            try {
                //获取读取文件
                fileInputStream = openFileInput(mFinalName);
                //设置一次读取字节数
                byte[] buff = new  byte[1024];
                //获取StringBuilder,实现字符串拼接
                StringBuilder sb = new StringBuilder("");
                int len = 0;
                //循环读取
                while ((len = fileInputStream.read(buff)) > 0){
                    sb.append(new String(buff,0,len));
                }
                //返回读取数据
                return sb.toString();
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                //关闭流
                if (fileInputStream!=null) {
                    try {
                        fileInputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
            return null;
        }
    }
    

    布局文件

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        android:padding="15dp">
        <EditText
            android:id="@+id/et_name"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:hint="输入内容"
            />
        <Button
            android:id="@+id/btn_save"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="保存"
            android:layout_marginTop="10dp"
            />
        <Button
            android:id="@+id/btn_show"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="显示"
            android:layout_marginTop="10dp"
            />
        <TextView
            android:id="@+id/tv_content"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginTop="10dp"
            />
    </LinearLayout>
    

    运行效果

    总结

    存储数据:

    • 获取FileOutputStream对象
    • 调用write()方法
    • 调用close()方法

    读取数据:

    • 获取FileInputStream对象
    • 调用read()方法
    • 调用close()方法

    File外部存储

    在SD中新建一个文件夹,在这个文件夹中新建一个文件,然后写入一些内容再读取出来。

    和内部存储原理是相同的,就是存储路径不同,一个在内部存储器上,一个在外部存储器。

    代码示例

    public class FileActivity extends AppCompatActivity {
    
        private EditText mEtName;
        private Button mBtnSave,mBtnShow;
        private TextView mTvContent;
    
        private final String mFinalName = "text.txt";
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_file);
    
            mEtName=findViewById(R.id.et_name);
            mBtnSave=findViewById(R.id.btn_save);
            mBtnShow=findViewById(R.id.btn_show);
            mTvContent=findViewById(R.id.tv_content);
    
    
    
            mBtnSave.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    save(mEtName.getText().toString().trim()); //trim()表示去除前后空格
                }
            });
    
            mBtnShow.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    mTvContent.setText(read());
                }
            });
        }
    
        //存储数据
        private void save(String content){
            FileOutputStream fileOutputStream=null;
            try {
    //            //外部存储
    //            fileOutputStream = openFileOutput(mFinalName,MODE_PRIVATE);
                //内部存储
                //创建文件夹
                File dir = new File(Environment.getExternalStorageState(),"FileStorage");
                if (!dir.exists()) {
                    dir.mkdirs();
                }
                //创建文件
                File file = new File(dir,mFinalName);
                if (!file.exists()) {
                    file.createNewFile();
                }
                fileOutputStream = new FileOutputStream(file);
                fileOutputStream.write(content.getBytes());
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                if (fileOutputStream!=null) {
                    try {
                        fileOutputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        }
    
        //读取数据
        private String read(){
            FileInputStream fileInputStream = null;
            try {
    //            //内部存储
    //            fileInputStream = openFileInput(mFinalName);
                //外部存储
                File file = new File(Environment.getExternalStorageDirectory().getAbsolutePath()+File.separator+"FileStorage",mFinalName);
                fileInputStream = new FileInputStream(file);
                byte[] buff = new  byte[1024];
                //实现字符串拼接
                StringBuilder sb = new StringBuilder("");
                int len = 0;
                while ((len = fileInputStream.read(buff)) > 0){
                    sb.append(new String(buff,0,len));
                }
                return sb.toString();
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                if (fileInputStream!=null) {
                    try {
                        fileInputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
            return null;
        }
    }
    
    

    布局文件和上面的一样:
    此外要在AndroidManifest.xml里添加两行代码,用来获取存储权限

        <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
        <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    

    这里在真机上运行出现如需下错误:

    暂时没有解决。

  • 相关阅读:
    BZOJ 3053 The Closest M Points
    Python 语言介绍
    计算机组成与操作系统基础
    Gym 100818I Olympic Parade(位运算)
    Codeforces 602B Approximating a Constant Range(想法题)
    Codeforces 599D Spongebob and Squares(数学)
    Codeforces 599C Day at the Beach(想法题,排序)
    ZOJ 3903 Ant(数学,推公示+乘法逆元)
    ZOJ 3911 Prime Query(线段树)
    UVALive 6910 Cutting Tree(离线逆序并查集)
  • 原文地址:https://www.cnblogs.com/yangdd/p/13376252.html
Copyright © 2020-2023  润新知