一、简介
1.文件存储
2.sd卡存储
3.sharepreferences存储
4.序列化xml文件
5.sqlite存储
二、文件存储
文件存储有两个主要的文件夹,一个是file文件夹,另一个是cache文件夹(这个文件夹放一些不重要的缓存文件或者配置文件)
- 可以通过getFilesDir()方法获得file文件
- 通过getCachesDir获取cache文件
- 通过getAbsolutePath()获取绝对路径
- 通过openFileOutout(文件名,模式)获取file的输出流
- 通过openFileInput(文件名)获取file的输入流
(注:这里的输入输出是相对程序自己的,不是file文件)
代码示例:
//布局文件就一个button
//点击按钮把一句话存到file文件下
//获取cache文件夹,只能用获取路径的方式
public class MainActivity extends AppCompatActivity {
OutputStream os=null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
public void click(View v){
try {
//os=new FileOutputStream(getFilesDir().getAbsolutePath()+"/hello.txt");//通过获取路径的方式获取输出流
os=openFileOutput("hello.txt",MODE_PRIVATE);//直接获取输出流
os.write("这仅仅只是一个测试".getBytes());
} catch (FileNotFoundException e) {
e.printStackTrace();
}catch(IOException e){
e.printStackTrace();
}finally{
if(os!=null){
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
三、SD卡存储
将文件存储的sd卡上
- 通过getExternalFilesDir(null)获取mnt/sdcard/Android/data/< package name >/files路径(当参数传null的时候默认是files,当传文件名的时候是files子文件路径)
- 通过getExternalStorageState()方法获取当前SD卡的状态
(MEDIA_MOUNTED为SD卡正常状态) - 通过Envirionment.getExternalStorageDirectory()获取sd卡根路径
(存储时不推荐用这个路径) - 通过根路径.getToalSpace()/getFreeSpace()分别获取总空间大小和剩余空间大小
- 通过Formatter.formatFileSize(Content con,size)将空间大小格式化
代码示例:
//讲一句话存入sd卡mnt/sdcard/Android/data/< package name >/files路径下
public class MainActivity extends AppCompatActivity {
OutputStream os=null;
TextView tv;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tv=findViewById(R.id.tv);
}
public void click(View view){
if(ActivityCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE)!= PackageManager.PERMISSION_GRANTED){
//动态申请权限
ActivityCompat.requestPermissions(this,new String[]{Manifest.permission.READ_EXTERNAL_STORAGE},1);
}else if(ActivityCompat.checkSelfPermission(this,Manifest.permission.WRITE_EXTERNAL_STORAGE)!=PackageManager.PERMISSION_GRANTED){
ActivityCompat.requestPermissions(this,new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},2);
}else{
if(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){
//判断sd卡状态,注意这里判断要用equals比较而不要用==判断
try {
File external=Environment.getExternalStorageDirectory();//获取根目录
long toalSpace=external.getTotalSpace();
long freeSpace=external.getFreeSpace();
//格式化空间大小
tv.setText("总空间:"+Formatter.formatFileSize(getApplicationContext(),toalSpace)+"剩余空间:"+Formatter.formatFileSize(getApplicationContext(),freeSpace));
//获取sd卡mnt/sdcard/Android/data/< package name >/files路径
File externlStorage = getExternalFilesDir(null);
Toast.makeText(this,externlStorage.getAbsolutePath(),Toast.LENGTH_LONG).show();
os = new FileOutputStream(externlStorage.getAbsolutePath() + "/hello.txt");
os.write("这仅仅只是个测试".getBytes());
}catch(FileNotFoundException e){
e.printStackTrace();
}catch(IOException e){
e.printStackTrace();
}
}
}
}
}
四、SharedPreferences存储
sharePreferences配置文件实质是一个xml文件,用来记录一些状态,类似记住用户名之类的
- 通过getSharedPreferences()获取SharePreferences对象
(这个对象只能用来读数据) - 通过SharedPreferences对象.edit()获得SharePreferences.Editor对象
(这个对象用来向里写数据) - SharedPreferences对象.getXXX()方法读数据
- Editor对象.putXXX()方法存数据
(数据是键值对的形式存储,最后一定要掉Editor对象.commit()提交)
代码示例:
//布局是一个TextView和两个Button
public class MainActivity extends AppCompatActivity {
SharedPreferences sp=null;
TextView tv;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tv=findViewById(R.id.tv);
sp=getSharedPreferences("hello", MODE_PRIVATE);//获取SharedPreferences对象
}
public void click(View view){
SharedPreferences.Editor editor=sp.edit();//获取Editor对象
editor.putString("hello","这仅仅只是一次测试");//写数据
editor.commit();
}
public void click1(View view){
tv.setText( sp.getString("hello",""));//读数据
}
}
运行结果:
运行结果五、xml文件的序列化和解析
xml序列化通过XMLSerializer对象进行序列化,通过XmlPullParser进行pull解析
(1)序列化
- 通过Xml.newSerializer()获取XmlSerializer对象
- setOutput(Writer writer)/setOutput(OutputStream os,String encoding)获取输出流
- startDocument(String encoding,boolean Standalone)/endDocument()开始Document和结束Document
- startTag(String nameSpace,String name)/endTag(String nameSpace,String name)开始和结束标签
- text(String text)设置文本
- setProperty(String name,Object value)设置属性
(2)解析
- Xml.newPullParser()获取XmlPullParser对象
- setInput(InputStream is,String encoding)设置输入
- getEventType()获取事件类型
- next()进入下一个事件
-getName()获取姓名
代码示例:
//序列化一个xml,然后解析出来
public class MainActivity extends AppCompatActivity {
TextView tv=null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tv=findViewById(R.id.tv);
}
public void click(View view){
XmlSerializer xml= Xml.newSerializer();//获取XmlSerializer对象
OutputStream os=null;
try {
os=openFileOutput("hello.xml",MODE_PRIVATE);
xml.setOutput(os,"utf-8");
xml.startDocument("utf-8",true);//开始Document
xml.startTag(null,"students");//开始标签
xml.startTag(null,"student");
xml.startTag(null,"name");
xml.text("jty");//设置文本
xml.endTag(null,"name");
xml.startTag(null,"number");
xml.text("1551654");
xml.endTag(null,"number");//结束标签
xml.endTag(null,"student");
xml.startTag(null,"student");
xml.startTag(null,"name");
xml.text("zcf");
xml.endTag(null,"name");
xml.startTag(null,"number");
xml.text("1551655");
xml.endTag(null,"number");
xml.endTag(null,"student");
xml.endTag(null,"students");
xml.endDocument();//结束Document
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally {
if(os!=null){
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
public void click1(View v){
XmlPullParser pull=Xml.newPullParser();//获取XmlpullParser对象
InputStream is=null;
StringBuffer str=new StringBuffer();
try {
is=openFileInput("hello.xml");
pull.setInput(is,"utf-8");
int eventType=pull.getEventType();//获取事件类型
while(eventType!=XmlPullParser.END_DOCUMENT){
switch (eventType){
case XmlPullParser.START_TAG:
if(pull.getName().equals("name")){//获取标签名
str.append("name:"+pull.nextText()+" ");
}else if (pull.getName().equals("number")){
str.append("number:"+pull.nextText()+" ");
}
break;
}
eventType=pull.next();//下一个事件并返回事件类型
}
tv.setText(str);
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (XmlPullParserException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
finally {
if(is!=null){
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
六、Sqlite存储
sqlite是Android自带的数据库十分轻量,跨平台,绿色解压就能用。
- 首先继承SqliteOpenHelper,这个类有一个构造方法,里面的参数分别为上下文、数据库的名字、游标工厂(一般为null)、版本号,需要实现onCreate()方法和onUpgrade()方法
(onCreate()数据库创建的时候会被调用,一般在这里面建表和初始化 ,onUpgrade()在版本升级的时候被调用,一般这里做表的修改和添加新的表等操作) - 通过 new SqliteOpenHelper()方法获取SqliteOpenHelper对象
- SqlieOpenHelper对象.getReadableDatabase()/getWriteableDatabase获i取database对象
(二者作用大部分时相同,都是打开或创建一个可读可写的数据库,当磁满的时候,第一个方法是返回一个可读的数据库第二个会失败) - 执行sql语句操作数据库,execsql用来执行增删改sql语句的,rawQuery执行查找操作sql语句查询的返回值为Cursor类型
- 用api执行数据库操作insert(表名,备用列名,Values)(Content Values values=new ContentValues valuse.put(列名,值)) / delete(表名,条件(XXX=?),问号的参数值数组({xxx,xxx})) / updata(表名,Content Values,条件(写法同delete),条件值数组(写法同delete)) / query(表名,列名(数组),条件,条件值,groupby(sql里的分组),having(条件,分组后的行条件),limit(结果限定))分别为插入/删除/更新/查询
- cursor操作通过moveToNext指向下一行/getXXX(列号)获取列号对应的值/getColumnIndex(键)获取键对应的列号
- 用close()方法关闭数据库(注:用完要关闭数据库)
代码示例:
(1)继承SqliteOpenHelper的类
public class MySqliteHelper extends SQLiteOpenHelper {//继承SqliteOpenHelper类
public MySqliteHelper(Context context){
super(context,"myDataBase",null,1);//构造方法
}
public void onCreate(SQLiteDatabase db){
db.execSQL("create table information(user_id integer primary key autoincrement,user_name varchar,user_age integer)");
//创建表,注意自增约束在sqlite为autoincrement,int类型要写integer
}
public void onUpgrade(SQLiteDatabase db,int oldVersion,int newVersion){
//升级版本在这里操作,本代码就不演示了
}
}
(2)Activity中的代码
public class MainActivity extends AppCompatActivity {
SQLiteDatabase db=null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
MySqliteHelper helper=new MySqliteHelper(this);//创建helper类
db=helper.getReadableDatabase();//获取数据库
}
public void click1(View view){
ContentValues values=new ContentValues();
values.put("user_name","jty");
values.put("user_age",10);
db.insert("information","user_id",values);//插入
ContentValues values1=new ContentValues();
values.put("user_name","zcf");
values.put("user_age",11);
db.insert("information","user_id",values);
}
public void click2(View view){
db.delete("information","user_name=?",new String[]{"jty"});//删除
}
public void click3(View view){
ContentValues values=new ContentValues();
values.put("user_age",15);
db.update("information",values,"user_name=?",new String[]{"zcf"});//更新
}
public void click4(View view){
Cursor cursor=db.query("information",new String[]{"user_id","user_name","user_age"},null,null,null,null,null);//
查找
while(cursor.moveToNext()){//指向下一条
Log.i("output","user_id:"+cursor.getInt(cursor.getColumnIndex("user_id")));
//获取值
Log.i("output","user_name:"+cursor.getString(cursor.getColumnIndex("user_name")));
Log.i("output","user_age:"+cursor.getInt(cursor.getColumnIndex("user_age")));
}
}
public void onDestroy() {
db.close();//在activity销毁时关闭数据库
super.onDestroy();
}
}
(3)扩展
事务的应用
db.beginTransaction();//开启事务
try{
//要做的事务
db.setTransactionSuccessful();//如果没问题置成成功
}finally{
db.endTransaction();//结束事务时会检查是否成功,如果没成功回滚
//其它操作
}
网友评论