Android | DataStrorage 与 ContentProvider

阿里云国内75折 回扣 微信号:monov8
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6

Android DataStorage And ContentProvider

数据持久化

存储方式
SharedPreferences在键值对中存储私有原始数据
文件存储-内部存储在设备内存中存储私有数据
文件存储-外部存储在共享的外部存储中存储公共数据
SQLite 数据库在私有数据库中存储结构化数据

SharedPreferences

使用键值对的方式来存储数据将数据存储到 SharedPreferences 中有以下几种方式

  • Context.getSharedPreferences(String name, int mode) 方法第一个参数用于指定 SharedPreferences 文件的名称如果指定的文件不存在则会创建一个 SharedPreferences 文件都是存放在 /data/data/<packagename>/shared_prefs/ 目录下的第二个参数用于指定操作模式。
  • Activity.getPreferences(int mode) 方法接收一个操作模式参数自动将当前 Activity 的类名作为 SharedPreferences 的文件名。储存数据分三步第一步调用 SharedPreferences 对象 edit() 方法获取一个对象第二部利用形如 putString() 的方法向对象中添加数据第三步调用 apply() 方法将添加的数据提交完成数据的存储。
  • PreferenceManager.getDefaultSharedPreferences(Context) 方法以包名加上 _preferences 作为文件名以 MODE_PRIVATE 模式创建 SP 文件即 packgeName_preferences.xml

在存储时用到的 SharedPreferences.Editor 中的每一种 put 方法都对应着一个 get 方式去读取数据接受两个参数一个是键另一个是找不到相应键值时返回的默认值。

文件存储

不对存储的内容进行任何格式化处理所有数据都是原封不动地保存到文件当中。并不适合用于保存一些较为复杂的结构型数据。

Context 类中提供了一个 openFileOutput() 方法可以用于将数据存储到指定的文件中。这个方法接收两个参数第一个参数是文件名在文件创建的时候使用注意这里指定的文件名不可以包含路径因为所有的文件都默认存储到 /data/data/<package name>/files/ 目录下第二个参数是文件的操作模式主要有 MODE_PRIVATEMODE_APPEND 两种模式可选默认是 MODE_PRIVATE 表示当指定相同文件名的时候所写入的内容将会覆盖原文件中的内容而 MODE_APPEND 则表示如果该文件已存在就往文件里面追加内容不存在就创建新文件。openFileOutput() 方法返回的是一个 FileOutputStream 对象得到这个对象之后就可以使用 Java流 的方式将数据写入文件中。

Context 类中还提供了一个 openFileInput() 方法用于从文件中读取数据接收一个参数即要读取的文件名然后系统会自动到 /data/data/<package name>/files/ 目录下加载这个文件并返回一个 FileInputStream 对象得到这个对象之后再通过流的方式就可以将数据读取出来。

SQLite 数据库存储

Android 提供了一个 SQLiteOpenHelper 帮助类借助这个类可以非常简单地对数据库进行创建和升级。SQLiteOpenHelper 中有两个抽象方法onCreate()onUpgrade()。我们必须在自己的帮助类里重写这两个方法然后分别在这两个方法中实现创建和升级数据库的逻辑。SQLiteOpenHelper 中还有两个非常重要的实例方法getReadableDatabase()getWritableDatabase() 。这两个方法都可以创建或打开一个现有的数据库如果数据库已存在则直接打开否则要创建一个新的数据库并返回一个可对数据库进行读写操作的对象。

SQLite 支持的数据类型包括integer 表示整型real 表示浮点型text 表示文本类型blob 表示二进制类型。primary key 关键字设置主键。

Android 支持直接通过 SQL 来进行数据的增删查改还提供了简单的辅助方式进行CRUD操作

  • insertSQLiteDatabase 中提供了一个 insert() 方法专门用于添加数据。它接收3个参数第一个参数是表名第二个参数用于在未指定添加数据的情况下给某些可为空的列自动赋值 NULL 第三个参数是一个 ContentValues 对象它提供了一系列的 put() 方法重载用于向 ContentValues 中添加数据只需要将表中的每个列名以及相应的待添加数据传入即可。
  • deleteSQLiteDatabase 中提供了一个 delete() 方法专门用于删除数据。这个方法接收3个参数第一个参数是表名第二、第三个参数用于约束删除某一行或某几行的数据不指定的话默认会删除所有行。
  • selectSQLiteDatabase 中提供了一个 query() 方法用于对数据进行查询需要的参数很多在下表中列出并与 SQL 做出比较。
  • updateSQLiteDatabase 中提供了一个 update() 方法用于对数据进行更新。这个方法接收4个参数第一个参数是表名指定更新哪张表里的数据第二个参数是 ContentValues 对象要把更新数据在这里组装进去第三、第四个参数用于约束更新某一行或某几行中的数据不指定的话默认会更新所有行。
query()方法SQL方法
tablefrom table_name指定查询的表名
columnsselect column1, column2指定查询的列名
selectionwhere column = value指定where的约束条件
selectionArgs-为where中的占位符提供具体的值
groupBygroup by column指定需要group by的列
havinghaving column = value对group by后的结果进一步约束
orderByorder by column1, column2指定查询结果的排序方式

ContentProvider 概念

主要用于在不同的应用程序之间实现数据共享的功能它提供了一套完整的机制允许一个程序访问另一个程序中的数据同时还能保证被访问数据的安全性。

访问其他程序中数据

对于每一个应用程序来说如果想要访问 ContentProvider 中共享的数据就一定要借助 ContentResolver 类可以通过 Context 中的 getContentResolver() 方法获取该类的实例。ContentResolver 中提供了一系列的方法用于对数据进行增删改查操作其中 insert() 方法用于添加数据update() 方法用于更新数据delete() 方法用于删除数据query() 方法用于查询数据。

// 外部进程 向 ContentProvider 中添加数据 
public Uri insert(Uri uri, ContentValues values); 

// 外部进程 删除 ContentProvider 中的数据 
public int delete(Uri uri, String selection, String[] selectionArgs);

// 外部进程 更新 ContentProvider 中的数据 
public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs); 

// 外部应用 获取 ContentProvider 中的数据 
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder);

这4个方法由外部进程回调并运行在 ContentProvider 进程的 Binder线程池 中不是主线程.

通过 URI(统一资源标识符) 分别不同App协议名为 content 。“主机名”为包名路径为需要访问的数据库表。

/**
[协议名]://[用户名]:[密码]@[主机名]:[端口]/[路径]?[查询参数]#[片段ID]

content://com.example.app.provider/table1
*/

URI uri = URI.parse("content://com.example.app.provider/table1");

总体使用逻辑如下

URI uri = URI.parse("content://com.example.app.provider/table1"); 
ContentResolver resolver = context.getContentResolver(); 
ContentValues values = new ContentValues(); 
values.put("_id", 1); 
values.put("name", "values1"); 
resolver.insert(uri, values);

创建 ContentProvider

如果想要实现跨程序共享数据的功能可以通过新建一个类去继承 ContentProvider 的方式来实现。ContentProvider 类中有6个抽象方法我们在使用子类继承它的时候需要将这6个方法全部重写。

// 外部进程 向 ContentProvider 中添加数据 
public Uri insert(Uri uri, ContentValues values); 

// 外部进程 删除 ContentProvider 中的数据 
public int delete(Uri uri, String selection, String[] selectionArgs);

// 外部进程 更新 ContentProvider 中的数据 
public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs); 

// 外部应用 获取 ContentProvider 中的数据 
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder);

// ContentProvider 创建后或打开系统后其它进程第一次访问该 ContentProvider 时由系统进行调用 
public boolean onCreate();

// 得到数据类型即返回当前 Url 所代表数据的 MIME 类型 
public String getType(Uri uri) { 
	//在此匹配URI 
	URIMatcher.match(uri) 
}

在注册创建的 ContentProvider 时需要将授权信息填写到 AndroidManifest

<provider 
	android:name="MyProvider" 
	android:authorities="com.example.mycontentprovider" 
/>
阿里云国内75折 回扣 微信号:monov8
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6
标签: android