~~~~~~~~~~SDK之ContentProvider学习笔记~~~~~~~~~~~
ContentProvider的作用如下:
Content providers store and retrieve data and make it accessible to all applications. They're the only way to share data across applications; there's no common storage area that all Android packages can access.
-------如果要自定义一个content provider,最好为它的uri定义一个常量,这样就方便客户端的代码以及后期的更新。每个content provider都会开放一个公共的URI(由一个Uri对象包装),这个URI唯一的标识了content provider的数据集。所有content provider的URI都是以字符串“content://"开始的。
URI常量使用在与content provider的所有交互中。
-------查询content provider:
查询一个content provider需要三方面的信息:
(1)标识provider的URI
(2)准备接受的数据域的名称
(3)这些数据域的数据类型
如果是要查找某个特定的记录,那么还需要知道那条记录的ID。
Making a query:
可以使用ContentResolver.query()或Activity.managerdQuery()方法。
上述两个查询函数的第一个参数都是content provider的uri。
如果想要将查询限制在某一条记录,可以在URI的后面添加那条记录的_ID值。可以通过
和ContentUris.withAppendedId()
Uri.withAppendedPath()来实现
对于查询返回的Cursor对象,只能使用它进行数据的读取,至于数据的增加、删除和修改同必须通过ContentSolver对象来实现。
Reading retrieved data:
Cursor对象提供了一些方法用于读取查询到的记录如:getString()/getInt()/getFloat(),但是这些方法的参数都是对应列的index,所以首先需要通过列名称来获得对应的index,才能读取数据。而Cursor对象本身就支持从列名称获得index,从index获得列名称的方法。如:Cursor.getColumnIndex().
modifying data:
由ContentProvider保存的数据可以在下面的几个方面进行修改:
(1)Adding new records
(2)Adding new values to existing records
(3)Batch updating existing records
(4)Deleting records
所有数据的修改都要通过ContentResolver的方法来实现。同时也要注意事先获得数据的修改权限,否则会修改失败。
(1)adding records:使用ContentValues对象和ContentResolver.insert()方法。
如果是向ContentProvider中存放图片、声音等大容量的多媒体信息时,一般都是在provider中暂时存放它们的uri而已,而打开的时候是通过ContentResolver.openOutputStream()方法实现的。
(2)adding new values:使用ContentResolver.insert()返回的uri做进一步的处理。
(3)batch updating records:使用
方法更新列的值。ContentResolver.update()
(4)deleting a record:使用ContentResolver.delete()
注意:android虚拟机中的应用程序的私有数据一般都是存放在/data/data/{包名}/databases下面的。如:contacts应用程序在/data/data/com.android.providers.contacts/databases/目录下,就存在了contacts2.db的SQLite的数据库文件。
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
如何创建ContentProvider?
主要包括如下的几个方面:
(1)Set up a system for storing the data.
注意: Android provides the SQLiteOpenHelper
class to help you create a database and SQLiteDatabase
to manage it.
(2)Extend the ContentProvider
class to provide access to the data.
注意:需要实现6个成员方法
query() insert()
update()
delete()
getType()
onCreate():当provider被启动的时候调用。
这些方法都可能被ContentResolver对象所调用。
call
to notify listeners when there are modifications to the data. ContentResolver.notifyChange()
定义ContentProvider的几个步骤:
----Define a
public static final
Uri
named CONTENT_URI
. This is the string that represents the full content:
URI that your content provider handles.
--------Define the column names that the content provider will return to clients.
--------Carefully document the data type of each column. Clients need this information to read the data.
--------If you are handling a new data type, you must define a new MIME type to return in your implementation of
.ContentProvider.getType()
(3)Declare the content provider in the manifest file for your application(AndroidManifest.xml).
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~··
学习小结:
提示:对于自定义的ContentProvider,由于其他的其他的应用程序很可能会使用其中的一些静态数据,所以可以将它导出为JAR归档文件。
开发Android应用程序时,一定要注意是否在AndroidManifext.xml文件中是否加入合适的访问权限,否则会导致莫名其妙的错误提示。
看完Android SDK中的ContentProvider中的内容之后:
Cursor、ContentProvider、ContentResolver三者之间的关系应该是这样的:
ContentProvider主要负责的是数据的存储和提供底层的数据维护操作,它是不和客户代码直接发生联系的。
ContentResolver主要负责客户端代码的工作,是直接响应UI界面的操作的,通过它来调用ContentProvider中的一些回调函数实现数据的增、删、改、查。
Cursor主要是显示从ContentProvider中获取的数据,它本身只能提供显示读取的功能,不能进行修改。
在SQLite实现数据维护操作,一般都是通过SQLiteOpenHelper的继承子类获得SQLiteDatabase对象实例,再来实现数据操作,这样比较方便。
在实际的编程开发中,一般不会直接使用Cursor的子类对象的操作来显示数据,而是通过将Cursor子类对象与适配器空间联系起来,进而实现数据的显示。