- 浏览: 155527 次
- 性别:
- 来自: 湖南
文章分类
最新评论
-
viking_wu:
Android POST方式提交数据 -
hsiunien:
不能正常调用 init android4.3上 是否可以 ...
Android JS双向调用 -
liaokang.java:
Apple.Chen 写道你确定这是插入排序而不是冒泡?插入排 ...
java之插入排序 -
Apple.Chen:
你确定这是插入排序而不是冒泡?
java之插入排序 -
ct19900913:
顶一个!!!
Android ContentProvider共享数据
ContentProvider的基本概念
a.ContentProvider为存储和读取数据提供了统一的接口
b.使用ContentProvider,应用程序可以实现数据共享
c.android内置的许多数据都是使用ContentProvider形式,供开发者调用的(如视频,音频,图片,通讯录等)
1.数据模型
Content Provider 将其存储的数据以数据表的形式提供给访问者,在数据表中每一行为一条记录,每一列为具有特定类型和意义的数据。每一条数据记录都包括一个 "_ID" 数值字段,改字段唯一标识一条数据。
2.Uri
Uri,每一个Content Provider 都对外提供一个能够唯一标识自己数据集(dataset)的公开URI, 如果一个Content Provider管理多个数据集,其将会为每个数据集分配一个独立的URI。所有的Content Provider 的URI 都以"content://" 开头,其中"content:"是用来标识数据是由Content Provider管理的 schema。
在几乎所有的Content Provider 的操作中都会用到Uri,因此一般来讲,如果是自己开发的Content Provider,最好将URI定义为常量,这样在简化开发的同时也提高了代码的可维护性。
我们将Uri分为A,B,C,D 4个部分:
A:标准前缀,用来说明一个Content Provider控制这些数据,无法改变的"content://"
B:Uri的标识,它定义了是哪个Content Provider提供这些数据。对于第三方应用程序,为了保证URI标识的唯一性,它必须是一个完整的,小写的类名。这个标识在元素的authorities属性中说明:一般是定义该ContentProvider的包.类的名称,如"content://com.lamp.provider.personprovider"
C:路径,Uri下的某一个Item,就像网站一样,主网页下包含很多小网页。这里通俗的讲就是你要操作的数据库中表的名字(比如我操作的表为person),或者你也可以自己定义,记得在使用的时候保持一致就ok了,如"content://com.lamp.provider.personprovider/person"
D:如果Uri中包含表示需要获取的记录的ID;则就返回该id对应的数据,如果没有ID,就表示对全部记录进行操作,例如content://com.lamp.provider.personprovider/person 针对表中所有记录
content://com.lamp.provider.personprovider/person/5 针对id为5的记录
UriMatcher:用于匹配Uri,它的用法如下:
1.首先把你需要匹配Uri路径全部给注册上。
1.常量UriMatcher.NO_MATCH表示不匹配任何路径的返回码(-1)。
UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
2.注册匹配的Uri
//content://com.lamp.provider.personprovider/person 针对表中所有记录,如果匹配该路径,返回1
uriMatcher.addURI(authority, "person", 1);
//content://com.lamp.provider.personprovider/person/# 针对符合条件的记录,如果匹配该路径,返回2
uriMatcher.addURI(authority, "person/#",2);
3.注册完需要匹配的Uri后,就可以使用uriMatcher.match(uri)方法对输入的Uri进行匹配,如果匹 配就返回匹配码,匹配码是调用 addURI()方法传入的第三个参数,假设匹配 content://com.lamp.provider.personprovider/person 路径,返回的匹配码为1。
ContentUris:用于获取Uri路径后面的ID部分,它有两个比较实用的方法:
withAppendedId(uri, id)用于为路径加上ID部分
parseId(uri)方法用于从路径中获取ID部分
下面是一个小例子来说明ContentProvider的使用
1.新建一个类来继承ContentProvider
2.在AndroidManifest.xml对ContentProvider进行配置,为了能使其它应用能找到该ContentProvider,ContentProvider采用了android:authorities对它进行唯一标识,你可以把ContentProvider看成是一个网站,authorities就是它的域名
3.由于我操作的数据是针对数据库,新建一个类继承SQLiteOpenHelper
4.用到的实体bean为Person
至此ContentProvider的配置完成,将项目部署到模拟器或者手机中,下面来编写一个新的应用来对上一个应用的数据进行测试
1.新建一个新的项目
记得在AndroidManifest.xml中注册权限
a.ContentProvider为存储和读取数据提供了统一的接口
b.使用ContentProvider,应用程序可以实现数据共享
c.android内置的许多数据都是使用ContentProvider形式,供开发者调用的(如视频,音频,图片,通讯录等)
1.数据模型
Content Provider 将其存储的数据以数据表的形式提供给访问者,在数据表中每一行为一条记录,每一列为具有特定类型和意义的数据。每一条数据记录都包括一个 "_ID" 数值字段,改字段唯一标识一条数据。
2.Uri
Uri,每一个Content Provider 都对外提供一个能够唯一标识自己数据集(dataset)的公开URI, 如果一个Content Provider管理多个数据集,其将会为每个数据集分配一个独立的URI。所有的Content Provider 的URI 都以"content://" 开头,其中"content:"是用来标识数据是由Content Provider管理的 schema。
在几乎所有的Content Provider 的操作中都会用到Uri,因此一般来讲,如果是自己开发的Content Provider,最好将URI定义为常量,这样在简化开发的同时也提高了代码的可维护性。
我们将Uri分为A,B,C,D 4个部分:
A:标准前缀,用来说明一个Content Provider控制这些数据,无法改变的"content://"
B:Uri的标识,它定义了是哪个Content Provider提供这些数据。对于第三方应用程序,为了保证URI标识的唯一性,它必须是一个完整的,小写的类名。这个标识在元素的authorities属性中说明:一般是定义该ContentProvider的包.类的名称,如"content://com.lamp.provider.personprovider"
C:路径,Uri下的某一个Item,就像网站一样,主网页下包含很多小网页。这里通俗的讲就是你要操作的数据库中表的名字(比如我操作的表为person),或者你也可以自己定义,记得在使用的时候保持一致就ok了,如"content://com.lamp.provider.personprovider/person"
D:如果Uri中包含表示需要获取的记录的ID;则就返回该id对应的数据,如果没有ID,就表示对全部记录进行操作,例如content://com.lamp.provider.personprovider/person 针对表中所有记录
content://com.lamp.provider.personprovider/person/5 针对id为5的记录
UriMatcher:用于匹配Uri,它的用法如下:
1.首先把你需要匹配Uri路径全部给注册上。
1.常量UriMatcher.NO_MATCH表示不匹配任何路径的返回码(-1)。
UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
2.注册匹配的Uri
//content://com.lamp.provider.personprovider/person 针对表中所有记录,如果匹配该路径,返回1
uriMatcher.addURI(authority, "person", 1);
//content://com.lamp.provider.personprovider/person/# 针对符合条件的记录,如果匹配该路径,返回2
uriMatcher.addURI(authority, "person/#",2);
3.注册完需要匹配的Uri后,就可以使用uriMatcher.match(uri)方法对输入的Uri进行匹配,如果匹 配就返回匹配码,匹配码是调用 addURI()方法传入的第三个参数,假设匹配 content://com.lamp.provider.personprovider/person 路径,返回的匹配码为1。
ContentUris:用于获取Uri路径后面的ID部分,它有两个比较实用的方法:
withAppendedId(uri, id)用于为路径加上ID部分
parseId(uri)方法用于从路径中获取ID部分
下面是一个小例子来说明ContentProvider的使用
1.新建一个类来继承ContentProvider
package com.lamp.db; import android.content.ContentProvider; import android.content.ContentUris; import android.content.ContentValues; import android.content.UriMatcher; import android.database.Cursor; import android.database.sqlite.SQLiteDatabase; import android.net.Uri; import android.text.TextUtils; import com.lamp.service.DataBaseOpenHelper; public class PersonContentProvider extends ContentProvider { private DataBaseOpenHelper dbHelper = null; private static UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH); private static final int ALLPERSON = 1; private static final int PERSON = 2; private static final String authority = "com.lamp.provider.personprovider"; private static String TABLENAME = "person"; static{ //content://com.lamp.provider.personprovider/person 针对表中所有记录,如果匹配该路径,返回1 uriMatcher.addURI(authority, TABLENAME, ALLPERSON); //content://com.lamp.provider.personprovider/person/# 针对符合条件的记录,如果匹配该路径,返回2 uriMatcher.addURI(authority, TABLENAME + "/#", PERSON); } @Override public boolean onCreate() { dbHelper = new DataBaseOpenHelper(this.getContext()); return true; } //删除数据 @Override public int delete(Uri uri, String selection, String[] selectionArgs) { SQLiteDatabase database = dbHelper.getWritableDatabase(); int count = 0; switch (uriMatcher.match(uri)) { case ALLPERSON: count = database.delete(TABLENAME, selection, selectionArgs); break; case PERSON: long personid = ContentUris.parseId(uri); String where = TextUtils.isEmpty(selection)?"personid=?":selection + " personid=?"; String[] params = new String[]{String.valueOf(personid)}; if(!TextUtils.isEmpty(selection) && selectionArgs!=null){ params = new String[selectionArgs.length+1]; for (int i = 0; i < selectionArgs.length; i++) { params[i] = selectionArgs[i]; } params[selectionArgs.length] = String.valueOf(personid); } count = database.delete(TABLENAME, where, params); break; default: throw new IllegalArgumentException("参数错误" + uri); } return count; } @Override public String getType(Uri uri) { switch (uriMatcher.match(uri)) { case ALLPERSON: return "vnd.android.cursor.dir/personprovider.person"; case PERSON: return "vnd.android.cursor.item/personprovider.person"; default: throw new IllegalArgumentException("参数错误" + uri); } } //插入数据 @Override public Uri insert(Uri uri, ContentValues values) { SQLiteDatabase database = dbHelper.getWritableDatabase(); long id = 0; switch (uriMatcher.match(uri)) { case ALLPERSON: id = database.insert(TABLENAME, "name", values); return ContentUris.withAppendedId(uri, id); case PERSON: id = database.insert(TABLENAME, "name", values); String uriString = uri.toString(); uriString = uriString.substring(0, uriString.lastIndexOf("/")) + id; return Uri.parse(uriString); default: throw new IllegalArgumentException("参数错误" + uri); } } //查询数据 @Override public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) { SQLiteDatabase database = dbHelper.getWritableDatabase(); switch (uriMatcher.match(uri)) { case ALLPERSON: return database.query(TABLENAME, projection, selection, selectionArgs, null, null, sortOrder); case PERSON: long personid = ContentUris.parseId(uri); String where = TextUtils.isEmpty(selection)?"personid=?":selection + " personid=?"; String[] params = new String[]{String.valueOf(personid)}; if(!TextUtils.isEmpty(selection) && selectionArgs!=null){ params = new String[selectionArgs.length+1]; for (int i = 0; i < selectionArgs.length; i++) { params[i] = selectionArgs[i]; } params[selectionArgs.length] = String.valueOf(personid); } return database.query(TABLENAME, projection, where, params, null, null, sortOrder); default: throw new IllegalArgumentException("参数错误" + uri); } } //更新数据 @Override public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) { SQLiteDatabase database = dbHelper.getWritableDatabase(); int count = 0; switch (uriMatcher.match(uri)) { case ALLPERSON: count = database.update(TABLENAME, values, selection, selectionArgs); break; case PERSON: long personid = ContentUris.parseId(uri); String where = TextUtils.isEmpty(selection)?"personid=?":selection + " personid=?"; String[] params = new String[]{String.valueOf(personid)}; if(!TextUtils.isEmpty(selection) && selectionArgs!=null){ params = new String[selectionArgs.length+1]; for (int i = 0; i < selectionArgs.length; i++) { params[i] = selectionArgs[i]; } params[selectionArgs.length] = String.valueOf(personid); } count = database.update(TABLENAME, values, where, params); break; default: throw new IllegalArgumentException("参数错误" + uri); } return count; } }
2.在AndroidManifest.xml对ContentProvider进行配置,为了能使其它应用能找到该ContentProvider,ContentProvider采用了android:authorities对它进行唯一标识,你可以把ContentProvider看成是一个网站,authorities就是它的域名
<application android:icon="@drawable/icon" android:label="@string/app_name"> <uses-library android:name="android.test.runner" /> <provider android:name=".PersonContentProvider" android:authorities="com.lamp.provider.personprovider"/> .....
3.由于我操作的数据是针对数据库,新建一个类继承SQLiteOpenHelper
package com.lamp.service; import android.content.Context; import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteOpenHelper; public class DataBaseOpenHelper extends SQLiteOpenHelper { private static final String DBNAME = "android"; private static final int VERSION = 1; public DataBaseOpenHelper(Context context) { super(context, DBNAME, null, VERSION); } @Override public void onCreate(SQLiteDatabase sqLiteDatabase) { String sql = "create table person (personid integer primary key autoincrement,name varchar(20),age integer)"; sqLiteDatabase.execSQL(sql); } @Override public void onUpgrade(SQLiteDatabase sqLiteDatabase, int oldVersion, int newVersion) { String sql = "drop table if exists person"; sqLiteDatabase.execSQL(sql); onCreate(sqLiteDatabase); } }
4.用到的实体bean为Person
package com.lamp.domain; public class Person { private Integer personid = null; private String name = null; private Integer age = null; public Person() { } public Person(String name,Integer age){ this.name = name; this.age = age; } public Integer getPersonid() { return personid; } public void setPersonid(Integer personid) { this.personid = personid; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Integer getAge() { return age; } public void setAge(Integer age) { this.age = age; } @Override public String toString() { return "personid:" + this.personid + "name: " + this.name + ", age:" + this.age; } }
至此ContentProvider的配置完成,将项目部署到模拟器或者手机中,下面来编写一个新的应用来对上一个应用的数据进行测试
1.新建一个新的项目
package com.lamp.provider; import android.app.Activity; import android.content.ContentResolver; import android.content.ContentValues; import android.net.Uri; import android.os.Bundle; import android.util.Log; public class PersonProviderTestActivity extends Activity { private static final String TAG = "PersonProviderTestActivity"; @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); ContentResolver cr = this.getContentResolver(); //通过唯一的Uri对特定的应用进行数据的操作 Uri uri = Uri.parse("content://com.lamp.provider.personprovider/person"); //插入数据 /* uri = Uri.parse("content://com.lamp.provider.personprovider/person"); ContentValues values = new ContentValues(); values.put("name", "kang"); values.put("age", 35); Uri uris = cr.insert(uri, values); */ //查询数据,此处是查询personid=13的记录 /* Uri uri = Uri.parse("content://com.lamp.provider.personprovider/person/13"); Cursor cursor = cr.query(uri, new String[]{"personid","name","age"}, null, null, null); while(cursor.moveToNext()){ Log.i(TAG, cursor.getInt(0) + " name:" + cursor.getString(1)); } cursor.close();*/ //测试删除,此处是删除personid=10的记录 uri = Uri.parse("content://com.lamp.provider.personprovider/person/10"); int count = cr.delete(uri, null, null); Log.i(TAG, String.valueOf(count)); //测试更新,此处是更新personid=14的记录 /* uri = Uri.parse("content://com.lamp.provider.personprovider/person/14"); ContentValues values2 = new ContentValues(); values2.put("name", "aaaaa"); values2.put("age", 35); int count = cr.update(uri, values2, null, null); Log.i(TAG, String.valueOf(count)); */ } }
记得在AndroidManifest.xml中注册权限
<uses-permission android:name="android.permission.READ_CONTACTS" />
发表评论
-
Android JS双向调用
2011-09-08 21:29 31482Android手机中内置了一款高性能webkit内核,该内核完 ... -
Android 音频播放
2011-09-08 10:22 2057android音频播放方式有两种:一种是MediaPlayer ... -
Android 流方式发送XML数据
2011-09-06 14:10 2565我们可以采用请求参数的形式向服务器发送数据,但是当数据太大时, ... -
Android POST方式提交数据
2011-09-05 19:53 13047android虽然内置了apache的 ... -
Android ListView详解
2011-08-31 22:18 1842在android应用中,数据以列表的形式显示通常是通过List ... -
Android采用Pull解析和生成xml文档
2011-08-29 19:03 2356Pull解析和Sax解析很相似,都是轻量级的解析,在Andro ... -
Android SAX解析xml文件
2011-08-28 18:39 1072andorid读取xml文件内容方法有三种 sax dom p ... -
Android之拨号器
2011-08-27 00:09 1409下面是用Android模拟拨号的小例子 首先是布局文件main ... -
Android之短信发送器
2011-08-27 00:03 1016虽然手机内置了短信发送器,但是有时候为了特定的需求项目 ...
相关推荐
"使用ContentProvider共享数据"这个主题涉及到如何构建和使用ContentProvider来开放数据库,以及如何通过ContentResolver来执行对这些共享数据的操作。 首先,理解ContentProvider的结构至关重要。ContentProvider...
在Android系统中,ContentProvider是实现应用程序间数据共享的核心组件。它允许一个应用将自己的数据集公开,让其他应用可以通过标准的ContentResolver接口进行访问。这种机制使得数据可以在多个应用之间透明地共享...
总结来说,ContentProvider是Android平台中实现数据共享的关键组件,通过定义Uri、注册到Manifest以及重写核心方法,我们可以创建一个能够跨应用共享数据的ContentProvider。同时,配合CursorLoader和LoaderManager...
`ContentProvider`是Android系统中用于不同应用程序间共享数据的一种核心组件。在本实验中,我们将学习如何创建和使用`ContentProvider`,以及如何通过`ContentResolver`和`ContentObserver`来与`ContentProvider`...
Android高级编程雪梨作业之自定义ContentProvider 将任务01生词本作业中生成的生词本数据库通过自定义ContentProvider的方式,共享给其他应用。 要求如下: (1) 使用自定义SQLiteOpenHelper来管理数据库; (2) 提交...
ContentProvider是Android系统中用于数据共享的一种机制,它可以使得应用的数据对其他应用可见并可操作。通过ContentProvider,我们可以实现跨应用的数据交换,比如联系人、日历等系统数据就是通过ContentProvider...
ContentProvider作为Android系统中数据共享的桥梁,允许不同的应用程序之间交换数据,而Observer模式则是一种设计模式,用于实现实时数据同步和更新。 **ContentProvider**是Android框架的一部分,它提供了一种标准...
在Android系统中,ContentProvider是四大组件之一,它扮演着数据共享和访问的重要角色。ContentProvider使得应用程序可以将自己的数据结构暴露给其他应用,同时也能够访问其他应用公开的数据。本篇文章将全面解析...
* 数据共享:ContentProvider 允许不同的应用程序之间共享数据,从而实现数据的共享和重用。 * 数据安全:ContentProvider 可以对数据进行保护,以免其他应用程序未经授权地访问数据。 * 灵活性:ContentProvider ...
总结来说,Content Provider的共享数据更新通知机制是通过ContentService、ContentResolver和ContentObserver三者的协作实现的。ContentService作为服务注册中心,ContentResolver作为通信桥梁,ContentObserver则...
在Android系统中,ContentProvider是一种核心组件,它允许应用程序之间共享和访问数据。ContentProvider封装了数据存储的方式,使得不同的应用可以透明地读写数据,而无需关心数据具体是如何存储的,例如SQLite...
`ContentProvider` 是Android提供的一种机制,允许应用间安全地共享数据。本篇将详细讲解如何利用`ContentProvider`来共享`SharedPreferences`的值。 首先,理解`SharedPreferences`。它是Android系统提供的一种轻...
ContentProvider(数据提供者)是在应用程序间共享数据的一种接口机制。应用程序在不同的进程中运行,因此,数据和文件在不同应用程序之间是不能够直接访问的。
在Android开发中,ContentProvider是一种重要的组件,它允许应用程序之间共享数据。本篇文章将深入探讨如何使用ContentProvider来共享生词本数据。首先,我们来看看什么是ContentProvider。 ContentProvider是...
在Android开发中,ContentProvider是一种重要的组件,它允许应用程序之间共享数据。本示例"android ContentProvider Demo"将深入探讨如何创建和使用ContentProvider来实现跨应用的数据交换。ContentProvider作为...
本篇将深入探讨如何使用ContentProvider对外共享数据以及如何监听内容提供者中的数据变化。 一、ContentProvider基础 ContentProvider是Android四大组件之一,它负责管理应用程序的数据,并提供统一的接口供其他...
在Android系统中,ContentProvider是四大组件之一,它扮演着数据共享的重要角色。ContentProvider使得应用程序之间能够安全、有序地访问彼此的数据,无论是保存在SQLite数据库中的数据,还是存储在文件系统或者其他...
在Android系统中,ContentProvider是一种核心组件,它允许应用程序之间共享数据,而无需直接访问对方的内部存储。在本教程中,我们将深入探讨如何利用ContentProvider来操作文件,以及其在跨应用数据传输中的作用。 ...
首先,ContentProvider是Android四大组件之一,它作为数据存储和访问的桥梁,允许不同应用之间共享数据。ContentProvider基于URI(统一资源标识符)来暴露数据,并通过标准的CRUD(创建、读取、更新、删除)操作管理...
在Android开发中,ContentProvider是四大组件之一,它充当了数据共享的桥梁,使得不同的应用程序之间可以安全地访问和共享数据。本篇文章将详细介绍如何在Android中实现一个简单的ContentProvider。 首先,理解...