目录
一、存储方式
在 Android Studio 中,可以使用多种方式来存储文件。以下是几种常用的文件存储方法:
-
内部存储:
- 调用
getFilesDir()
方法获取应用程序的内部存储目录。 - 使用该目录可以在应用私有目录下创建文件和目录,只有应用本身可以访问这些文件。
- 可以使用 Java 的
File
类或者 Kotlin 的java.io.File
进行文件操作。
- 调用
-
外部存储:
- 调用
Environment.getExternalStorageDirectory()
方法获取外部存储目录。 - 需要声明适当的权限(例如
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
)。 - 在 Android 10(API 级别 29)及更高版本中,需要使用 MediaStore API 或 SAF(Storage Access Framework)来访问外部存储上的文件。
- 调用
-
SharedPreferences:
- 使用 SharedPreferences 可以方便地存储小量的键值对数据。
- 通过
getSharedPreferences()
或getPreferences()
方法获取 SharedPreferences 对象。 - 使用 SharedPreferences 对象的
edit()
方法开始编辑,并通过putXxx()
方法存储数据。
-
SQLite 数据库:
- 如果需要存储大量结构化数据,可以使用 SQLite 数据库。
- 需要创建表、定义模型类和执行 SQL 操作。
- 可以使用 Android 提供的 SQLiteOpenHelper 类或第三方库来辅助管理数据库操作。
根据具体需求和数据量的大小,选择适合的文件存储方式。记得在使用外部存储时要处理权限问题和适应 Android 10 及以上版本的存储访问变更。
二、存储过程之存入
使用 openFileOutput()
方法将数据存储到内部存储中的文件:
String filename = "data";
String content = "要存储的内容";
try {
FileOutputStream fos = openFileOutput(filename, MODE_PRIVATE);
fos.write(content.getBytes());
fos.close();
// 存储成功
} catch (IOException e) {
e.printStackTrace();
// 存储失败,处理异常
}
上述代码中:
openFileOutput()
方法用于打开一个输出流并指定文件名和文件模式(这里使用MODE_PRIVATE
表示只有当前应用可以访问该文件)。write()
方法将内容以字节形式写入输出流。- 最后,通过
close()
方法关闭输出流,确保数据保存完成。
请注意,在使用 openFileOutput()
存储文件时,会覆盖同名文件。如果需要追加内容而不是覆盖原有内容,请使用其他方法(如使用 openFileInput()
读取文件内容,然后再追加新内容后重新写入)。
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".DictionaryTableActivity">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:ignore="MissingConstraints"
tools:layout_editor_absoluteX="26dp"
tools:layout_editor_absoluteY="0dp">
<EditText
android:id="@+id/edit_1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:autofillHints="username"
android:hint="输入内容"
tools:ignore="MissingConstraints"/>
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
public class DictionaryTableActivity extends AppCompatActivity implements View.OnClickListener {
private EditText editText;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_dictionary_table);
editText = (EditText) findViewById(R.id.edit_1);
}
@Override
protected void onDestroy() {
super.onDestroy();
String input = editText.getText().toString();
save(input);
}
private void save(String input){
FileOutputStream fileOutputStream = null;
BufferedWriter writer = null;
try {
fileOutputStream = openFileOutput("data", Context.MODE_PRIVATE);
writer = new BufferedWriter(new OutputStreamWriter(fileOutputStream));
writer.write(input);
}catch (Exception e){
e.printStackTrace();
}finally {
try {
if (writer != null){
writer.close();
}
}catch (Exception e){
e.printStackTrace();
}
}
}
三、存储过程之取出
public class DictionaryTableActivity extends AppCompatActivity implements View.OnClickListener {
private EditText editText;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_dictionary_table);
editText = (EditText) findViewById(R.id.edit_1);
editText.setText(load());
editText.setSelection(load().length());
}
private String load(){
FileInputStream fileInputStream = null;
BufferedReader reader = null;
StringBuilder stringBuffer = new StringBuilder();
try {
fileInputStream = openFileInput("data");
reader = new BufferedReader(new InputStreamReader(fileInputStream));
String Line ="";
while ( (Line = reader.readLine()) != null){
stringBuffer.append(Line);
}
}catch (Exception e){
e.printStackTrace();
}finally {
try {
assert reader != null;
reader.close();
}catch (Exception e){
e.printStackTrace();
}
}
return stringBuffer.toString();
}
四、openFileOutput()
方法的多种模式(mode
)
常用的模式及需要注意的事项:
-
MODE_PRIVATE
:- 模式常量:
0
或Context.MODE_PRIVATE
- 只有当前应用可以访问该文件。
- 如果指定的文件不存在,则创建新文件;如果文件已存在,则覆盖原有内容。
- 注意不要将重要、敏感或机密的数据存储在具有
MODE_PRIVATE
模式的文件中,因为其他应用无法访问。
- 模式常量:
-
MODE_APPEND
:- 模式常量:
Context.MODE_APPEND
- 文件写入时追加内容而不覆盖原有内容。
- 如果指定的文件不存在,则创建新文件。
- 适用于需要在现有文件的末尾添加数据的场景。
- 模式常量:
-
MODE_WORLD_READABLE
:- 模式常量:
Context.MODE_WORLD_READABLE
- 允许其他应用读取该文件。
- 不建议使用此模式,因为可能会导致数据泄露和安全问题。
- Android 7.0 及以上版本不支持该模式。
- 模式常量:
-
MODE_WORLD_WRITEABLE
:- 模式常量:
Context.MODE_WORLD_WRITEABLE
- 允许其他应用写入该文件。
- 不建议使用此模式,因为可能会导致数据泄露和安全问题。
- Android 7.0 及以上版本不支持该模式。
- 模式常量:
在选择存储模式时,请根据具体需求和安全考虑进行选择。尽量避免使用 MODE_WORLD_READABLE
和 MODE_WORLD_WRITEABLE
,以保护数据安全性。如果需要追加内容而不覆盖原有内容,可以使用 MODE_APPEND
模式。对于普通的私有文件,使用默认的 MODE_PRIVATE
即可满足大多数情况的需求。