- 浏览: 586089 次
- 性别:
- 来自: 上海
文章分类
- 全部博客 (182)
- android/ophone开发完全讲义 (4)
- android常用代码 (6)
- android工具 (9)
- android基础 (40)
- android进阶 (75)
- android经验记录 (3)
- android框架 (2)
- android面经 (5)
- android网络 (5)
- android资讯 (0)
- android资源 (17)
- 生活印象 (3)
- androidNDK (4)
- android开源 (1)
- android性能优化 (1)
- android设计 (2)
- android博客论坛收集 (1)
- android手机用户体验 (1)
- android动画 (1)
- android外文资料 (1)
- 汉字排序 (1)
最新评论
-
小猫咪201:
困惑了很久,终于找到答案了
一个常见的android内存泄露 问题 -
王雪龙:
pixels = dps * (density / 160). ...
关于Android的nodpi,xhdpi,hdpi,mdpi,ldpi -
Turr:
楼主给力,解决了我遇到的问题
解决ActivityGroup的sub Activity中spinner的WindowManager$BadTokenException的问题 -
boyuan2000cn:
你好,我转载了您的此篇博客,如果有版权问题,请告诉我,谢谢!转 ...
关于Android的nodpi,xhdpi,hdpi,mdpi,ldpi -
twlkyao:
请教您个问题,如何将drawable对象转换为id类型?
Android中Bitmap, Drawable, Byte,ID之间的转化
Android ContentProvider的介绍(很详细)
- 博客分类:
- android进阶
一、ContentProvider的概念
ContentProvider:为存储和获取数据提供统一的接口。可以在不同的应用程序之间共享数据。Android已经为常见的一些数据提供了默认的ContentProvider
1、ContentProvider使用表的形式来组织数据
无论数据的来源是什么,ContentProvider都会认为是一种表,然后把数据组织成表格
2、ContentProvider提供的方法
query:查询
insert:插入
update:更新
delete:删除
getType:得到数据类型
onCreate:创建数据时调用的回调函数
3、每个ContentProvider都有一个公共的URI,这个URI用于表示这个ContentProvider所提供的数据。Android所提供的ContentProvider都存放在android.provider包当中
二、ContentProvider的内部原理
自定义一个ContentProvider,来实现内部原理
步骤:
1、定义一个CONTENT_URI常量(里面的字符串必须是唯一)
Public static final Uri CONTENT_URI = Uri.parse("content://com.WangWeiDa.MyContentprovider");
如果有子表,URI为:
Public static final Uri CONTENT_URI = Uri.parse("content://com.WangWeiDa.MyContentProvider/users");
2、定义一个类,继承ContentProvider
Public class MyContentProvider extends ContentProvider
3、实现ContentProvider的所有方法(query、insert、update、delete、getType、onCreate)
package com.WangWeiDa.cp;
import java.util.HashMap;
import com.WangWeiDa.cp.MyContentProviderMetaData.UserTableMetaData;
import com.WangWeiDa.data.DatabaseHelp;
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.database.sqlite.SQLiteQueryBuilder;
import android.net.Uri;
import android.text.TextUtils;
public class MyContentProvider extends ContentProvider {
//访问表的所有列
public static final int INCOMING_USER_COLLECTION = 1;
//访问单独的列
public static final int INCOMING_USER_SINGLE = 2;
//操作URI的类
public static final UriMatcher uriMatcher;
//为UriMatcher添加自定义的URI
static{
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
uriMatcher.addURI(MyContentProviderMetaData.AUTHORITIES,"/user",
INCOMING_USER_COLLECTION);
uriMatcher.addURI(MyContentProviderMetaData.AUTHORITIES,"/user/#",
INCOMING_USER_SINGLE);
}
private DatabaseHelp dh;
//为数据库表字段起别名
public static HashMap userProjectionMap;
static
{
userProjectionMap = new HashMap();
userProjectionMap.put(UserTableMetaData._ID,UserTableMetaData._ID);
userProjectionMap.put(UserTableMetaData.USER_NAME, UserTableMetaData.USER_NAME);
}
/**
* 删除表数据
*/
@Override
public int delete(Uri uri, String selection, String[] selectionArgs) {
System.out.println("delete");
//得到一个可写的数据库
SQLiteDatabase db = dh.getWritableDatabase();
//执行删除,得到删除的行数
int count = db.delete(UserTableMetaData.TABLE_NAME, selection, selectionArgs);
return count;
}
/**
* 数据库访问类型
*/
@Override
public String getType(Uri uri) {
System.out.println("getType");
//根据用户请求,得到数据类型
switch (uriMatcher.match(uri)) {
case INCOMING_USER_COLLECTION:
return MyContentProviderMetaData.UserTableMetaData.CONTENT_TYPE;
case INCOMING_USER_SINGLE:
return MyContentProviderMetaData.UserTableMetaData.CONTENT_TYPE_ITEM;
default:
throw new IllegalArgumentException("UnKnown URI"+uri);
}
}
/**
* 插入数据
*/
@Override
public Uri insert(Uri uri, ContentValues values) {
//得到一个可写的数据库
SQLiteDatabase db = dh.getWritableDatabase();
//向指定的表插入数据,得到返回的Id
long rowId = db.insert(UserTableMetaData.TABLE_NAME, null, values);
if(rowId > 0){//判断插入是否执行成功
//如果添加成功,利用新添加的Id和
Uri insertedUserUri = ContentUris.withAppendedId(UserTableMetaData.CONTENT_URI, rowId);
//通知监听器,数据已经改变
getContext().getContentResolver().notifyChange(insertedUserUri, null);
return insertedUserUri;
}
return uri;
}
/**
* 创建ContentProvider时调用的回调函数
*/
@Override
public boolean onCreate() {
System.out.println("onCreate");
//得到数据库帮助类
dh = new DatabaseHelp(getContext(),MyContentProviderMetaData.DATABASE_NAME);
return false;
}
/**
* 查询数据库
*/
@Override
public Cursor query(Uri uri, String[] projection, String selection,
String[] selectionArgs, String sortOrder) {
//创建一个执行查询的Sqlite
SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
//判断用户请求,查询所有还是单个
switch(uriMatcher.match(uri)){
case INCOMING_USER_COLLECTION:
//设置要查询的表名
qb.setTables(UserTableMetaData.TABLE_NAME);
//设置表字段的别名
qb.setProjectionMap(userProjectionMap);
break;
case INCOMING_USER_SINGLE:
qb.setTables(UserTableMetaData.TABLE_NAME);
qb.setProjectionMap(userProjectionMap);
//追加条件,getPathSegments()得到用户请求的Uri地址截取的数组,get(1)得到去掉地址中/以后的第二个元素
qb.appendWhere(UserTableMetaData._ID + "=" + uri.getPathSegments().get(1));
break;
}
//设置排序
String orderBy;
if(TextUtils.isEmpty(sortOrder)){
orderBy = UserTableMetaData.DEFAULT_SORT_ORDER;
}
else{
orderBy = sortOrder;
}
//得到一个可读的数据库
SQLiteDatabase db = dh.getReadableDatabase();
//执行查询,把输入传入
Cursor c = qb.query(db, projection, selection, selectionArgs, null, null, orderBy);
//设置监听
c.setNotificationUri(getContext().getContentResolver(), uri);
return c;
}
/**
* 更新数据库
*/
@Override
public int update(Uri uri, ContentValues values, String selection,
String[] selectionArgs) {
System.out.println("update");
//得到一个可写的数据库
SQLiteDatabase db = dh.getWritableDatabase();
//执行更新语句,得到更新的条数
int count = db.update(UserTableMetaData.TABLE_NAME, values, selection, selectionArgs);
return count;
}
}
4、在AndroidMinifest.xml中进行声明
android:name=".cp.MyContentProvider"
android:authorities="com.WangWeiDa.cp.MyContentProvider"
/>
**为ContentProvider提供一个常量类MyContentProviderMetaData.java
package com.WangWeiDa.cp;
import android.net.Uri;
import android.provider.BaseColumns;
public class MyContentProviderMetaData {
//URI的指定,此处的字符串必须和声明的authorities一致
public static final String AUTHORITIES = "com.wangweida.cp.MyContentProvider";
//数据库名称
public static final String DATABASE_NAME = "myContentProvider.db";
//数据库的版本
public static final int DATABASE_VERSION = 1;
//表名
public static final String USERS_TABLE_NAME = "user";
public static final class UserTableMetaData implements BaseColumns{
//表名
public static final String TABLE_NAME = "user";
//访问该ContentProvider的URI
public static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITIES + "/user");
//该ContentProvider所返回的数据类型的定义
public static final String CONTENT_TYPE = "vnd.android.cursor.dir/vnd.myprovider.user";
public static final String CONTENT_TYPE_ITEM = "vnd.android.cursor.item/vnd.myprovider.user";
//列名
public static final String USER_NAME = "name";
//默认的排序方法
public static final String DEFAULT_SORT_ORDER = "_id desc";
}
}
评论
CONTENT_TYPE = "vnd.android.cursor.dir/vnd.myprovider.user";
CONTENT_TYPE_ITEM = "vnd.android.cursor.item/vnd.myprovider.user";
"vnd.android.cursor.dir/vnd."和"vnd.android.cursor.item/vnd"是什么意思?
uriMatcher.addURI(MyContentProviderMetaData.AUTHORITIES,"/user",
INCOMING_USER_COLLECTION);
uriMatcher.addURI(MyContentProviderMetaData.AUTHORITIES,"/user/#",
INCOMING_USER_SINGLE);
这里不能写成,/user,/user/#,必须写成user,user/#
发表评论
-
Android 检查当前是否已经连接上 Internet
2012-02-27 09:28 1java代码: 1 ConnectivityManager ... -
对ContentProvider中getType(Uri uri)和android.intent.category.DEFAULT的理解
2012-02-27 09:21 1633学习了ContentProvider,想做个通讯录,结果 ... -
一个常见的android内存泄露 问题
2012-02-20 16:11 4943最近在公司看一个算比较大的android项目的源码, ... -
一个常见的android内存泄露 问题
2012-02-20 16:10 0最近在公司看一个算比较大的android项目的源码,发 ... -
Android网络电台的一种实现方案
2012-02-20 15:12 3678随着电子产品的飞速 ... -
NotificationManager和Notification的使用总结
2012-02-16 15:55 1141这几天一直在修改twigee的源代码,其中一个要加入的 ... -
android 如何判断程序是否在前台运行
2012-02-16 15:31 5455private boolean isTopActivit ... -
Android Intent和PendingIntent的区别详细分析
2012-02-16 14:08 1567刚才一个例子中用到了PendingIntent,与之前学过的I ... -
编码问题(UTF-8、gb2312、unicode)
2012-02-14 09:38 1957相信大家很多人跟我一样,对于编码一直感觉云山雾罩,说知道吧?就 ... -
关于androidSDK登录时出现oauth2.0空白页的BUG
2012-02-09 16:21 1428在RenrenListenerFactory中,line 12 ... -
java中yield(),sleep()以及wait()的区别
2012-01-31 18:41 959往往混淆了这三个函数的使用。 从操作系统的角度讲, ... -
Toast大全(五种情形)建立属于你自己的Toast
2012-01-29 17:23 1594Toast用于向用户显示一些帮助/提示。下面我做了5中效果 ... -
Android主流屏幕分辨率介绍
2012-01-18 14:45 1421对于Android游戏开发我们不得不像iPhone那样思 ... -
关于混淆外包jar包出错的解决方法
2012-01-18 11:30 1797-optimizationpasses 5-do ... -
新浪微博SDK
2011-12-28 16:38 1198DEMO程序:http://code.google.co ... -
Android中自定义Dialog外形,去除黑底和白色边框
2011-12-08 16:29 7472在做Android开发中经常会使用到自定义样式的Dialo ... -
汉字排序
2011-12-07 09:44 1096Comparator comparator = Coll ... -
Android TextView中文字通过SpannableString来设置超链接、颜色、字体等属性
2011-11-29 19:29 13645在Android中,TextView是我们最常用的用来显示文本 ... -
屏幕分辨率适配
2011-10-19 18:55 3140屏幕分辨率:1024x600 d ... -
演化理解 Android 异步
2011-10-07 20:34 1078在学习"Android异步加载图像小结" ...
相关推荐
在Android应用开发中,数据持久化是一个至关重要的环节,而Android Room和ContentProvider是其中的两个关键组件。本文将深入探讨这两个技术,并结合实际案例,解释如何在Android应用中使用它们来管理和共享SQLite...
在Android系统中,ContentProvider是四大组件之一,它扮演着数据共享和访问的重要角色。ContentProvider使得应用程序可以将自己的数据结构暴露给其他应用,同时也能够访问其他应用公开的数据。本篇文章将全面解析...
在Android系统中,ContentProvider是一种核心组件,它允许应用程序之间共享数据,而无需直接访问对方的内部存储。在本教程中,我们将深入探讨如何利用ContentProvider来操作文件,以及其在跨应用数据传输中的作用。 ...
在"oldS1_ContentProvider"和"Test"这两个文件中,"oldS1_ContentProvider"很可能包含了ContentProvider的具体实现,包括URI匹配、数据操作和权限控制。而"Test"文件可能是用来测试ContentProvider功能的类,通过...
本篇文章将详细介绍如何在Android中实现一个简单的ContentProvider。 首先,理解ContentProvider的基本概念。ContentProvider是Android系统提供的一种机制,用于封装和暴露数据。它基于URI(统一资源标识符)来操作...
在Android系统中,ContentProvider是四大组件之一,它扮演着数据共享的角色,使得不同应用程序间可以安全地交换数据。本示例将深入讲解如何创建和使用ContentProvider。 首先,我们来理解ContentProvider的基本概念...
本示例将详细解释如何在Android中使用ContentProvider。 1. **ContentProvider基本概念** ContentProvider是Android系统提供的一种数据存储和访问机制,它允许应用程序之间进行数据交换,而无需暴露底层数据库或...
### android ContentProvider 详解 #### 一、ContentProvider 概述 ContentProvider 是 Android 四大组件之一,它主要用于在不同的应用程序之间实现数据共享。在 Android 中,每个应用程序都有自己的私有存储空间...
在Android开发中,ContentProvider和Observer模式是两个关键的概念,它们在数据管理和更新中起着重要作用。ContentProvider作为Android系统中数据共享的桥梁,允许不同的应用程序之间交换数据,而Observer模式则是一...
ContentProvider则是Android框架提供的一种机制,用于在应用程序之间共享数据,同时也可用于管理SQLite数据库。接下来,我们将深入探讨如何使用ContentProvider和SQLite在Android应用中执行数据库操作。 首先,...
在Android开发中,ContentProvider是四大组件之一,它扮演着数据共享的重要角色。ContentProvider使得应用程序之间能够安全、有序地访问彼此的数据,无论是系统内置的数据(如联系人、日历等)还是自定义的数据存储...
博文链接中提到的"sunzone.iteye.com/blog/1884167"可能详细介绍了如何根据上述步骤创建一个自定义的ContentProvider。通过阅读这个博客,你可以获取具体的代码示例和实现细节。 10. **最佳实践** - 数据访问应尽...
Android基于ContentProvider的音乐播放器,通过读取系统多媒体信息,得到储存在外部存储器上的所有音频文件内容,用listview显示歌曲名和歌手信息.并通过mediaPlayer进行播放.该版本只是完成了一个音乐播放器的最简单...
在Android系统中,ContentProvider是四大组件之一,它充当了数据共享的桥梁,使得不同的应用程序之间可以安全地读写数据。本篇文章将深入探讨ContentProvider的创建与访问过程,帮助你更好地理解和应用这一核心功能...
"Android Intent 和 ContentProvider" Android Intent 是 Android 组件之间的信使,负责在 Android 三大核心组件(Activity、Service、Broadcast Receiver)之间传递信息。Intent 是一个将要执行的动作的抽象描述...
在Android开发中,ContentProvider是一种核心组件,它允许应用程序间共享数据。ContentProvider构建于Android的URI机制之上,为其他应用提供了结构化的数据访问接口。本篇将详细讲解如何自定义ContentProvider,以及...
在Android应用开发中,ContentProvider是一个至关重要的组件,它扮演着数据共享的角色,使得不同的应用程序之间可以安全地读写共享数据。"android contentprovider的例子"这个主题将带你深入理解ContentProvider的...
在Android系统中,ContentProvider是实现数据共享和跨应用数据访问的重要组件。它遵循统一的URI(Uniform Resource Identifier)机制,使得不同的应用可以方便地读取和修改存储在ContentProvider中的数据。本教程将...
在Android系统中,ContentProvider是实现跨应用数据共享的关键组件,它允许应用程序暴露自己的数据集,使得其他应用可以通过标准的接口进行访问。本教程将深入解析ContentProvider的使用及其源码,结合SQLite数据库...