使用ContentProvider进行应用程序间的数据交互
什么是ContentProvider:
ContentProvider用来管理数据的访问规则。它允许你的应用程序向外界暴露需要被访问的数据。
是Android的四大组件之一。
ContentProviders支持四种基本的操作,即我们平时所见到的CRUD操作(增删改查)。Android系统
本身已经提供了一些内容提供者,它们允许我们查询联系人,媒体库,和短息消息等。
基于Content Uri的查询:
没有Uri,ContentProvider 类基本无法工作,就像我们上网没有网址。当我们要上网,就要在地址栏输入网址。
因此,要了解ContentProvider,我们必须先了解 Content Uri
下面是Uri的基本格式:
- content://authority/optionalPath/optionalId
content://是内容提供者的标准前缀,而且它必须是content://。authority由我们自己定义,它必须具有唯一性,
因此我们一般使用应用程序包名命名authority。optionalPath和optionalId是可选的。
下面我们来看一下WordPress的文章地址格式:
http://www.whathecode.com/archives/221
http:// 是http协议的标准写法,它是规定的,没有为什么。
www.whathecode.com可以理解为authority,因为域名是唯一的,它可以分辨我们要访问哪一个网站。
arichives可以理解为文章的分类。
最后的221就是文章的id,假如我们要查看第一遍文章,只要将221改成1就可以。
这样理解Uri是不是简单了很多。
建立自己的ContentProvider
建立ContentProvider只需几部:
1. 设计数据库的储存方式,因为ContentProvider提供的是数据,没有数据,ContentProvider就没有了用处。
2. 定义自己的类,继承ContentProvider类,并实现基本的方法。
3. 设计authority字符串。(要被人访问你的网站,你就需要一个网址,当然ip地址也可以)
4. 在AndroidManifest中注册Provider
我们先来研究一下代码:
作为示例下面的代码只实现了query方法,而且只添加了一个Uri,
一般应用程序都不只一个Uri
- package com.whathecode.provider;
- import android.content.ContentProvider;
- import android.content.ContentValues;
- import android.content.Context;
- import android.content.Intent;
- import android.content.UriMatcher;
- import android.database.Cursor;
- import android.database.sqlite.SQLiteDatabase;
- import android.database.sqlite.SQLiteDatabase.CursorFactory;
- import android.database.sqlite.SQLiteOpenHelper;
- import android.net.Uri;
- import android.util.Log;
- import android.widget.Toast;
- public class MemberProvider extends ContentProvider
- {
- private static final UriMatcher sMatcher;
- private static final String MEMBER_NAME = "name";
- private static final int QUERY_BY_NAME = 0;
- private static final String DB_NAME = "member.db";
- private static final String TAG = "MemberProvider";
- static
- {
- sMatcher = new UriMatcher(UriMatcher.NO_MATCH);
- /**
- * 添加需要匹配的Uri, 当这个Uri被匹配的时候返回第三个参数。
- * 得到这个参数之后就可以在query,insert,update,delete
- * 方法中做出相应的动作。
- */
- sMatcher.addURI(Member.AUTHORITY, MEMBER_NAME, QUERY_BY_NAME);
- }
- private static class DataBaseHelper extends SQLiteOpenHelper
- {
- public DataBaseHelper(Context context, String name,
- CursorFactory factory, int version)
- {
- super(context, name, factory, version);
- }
- @Override
- public void onCreate(SQLiteDatabase db)
- {
- //建立数据库表结构
- db.execSQL("create table member(_id integer primary key," +
- "name varchar(20)," +
- "work varchar(20)," +
- "age integer)");
- }
- @Override
- public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion)
- {
- // TODO Auto-generated method stub
- }
- }
- private DataBaseHelper mHelper;
- @Override
- public boolean onCreate()
- {
- mHelper = new DataBaseHelper(getContext(), DB_NAME, null, 2);
- return true;
- }
- @Override
- public Cursor query(Uri uri, String[] projection, String selection,
- String[] selectionArgs, String sortOrder)
- {
- /**
- * 前面我们在静态代码块中已添加了Uri库
- * 当每个Uri作为参数传进来的时候我们都先进行匹配
- *
- */
- switch (sMatcher.match(uri))
- {
- case QUERY_BY_NAME:
- //第一次执行时生成数据库member.db
- SQLiteDatabase readableDatabase = mHelper.getReadableDatabase();
- /**
- * 当query方法执行的时候向外发送广播
- */
- Intent intent = new Intent();
- intent.setAction("com.contentprovider.execquery");
- intent.putExtra("MemberProvider", "query方法执行了");
- getContext().sendBroadcast(intent);
- break;
- default:
- /**
- * 当Uri匹配失败的时候说明Uri参数错误,无法继续进行操作,
- * 因此程序抛出一个错误
- */
- throw new IllegalArgumentException("Unknown URI " + uri);
- }
- return null;
- }
- @Override
- public String getType(Uri uri)
- {
- // TODO Auto-generated method stub
- return null;
- }
- @Override
- public Uri insert(Uri uri, ContentValues values)
- {
- // TODO Auto-generated method stub
- return null;
- }
- @Override
- public int delete(Uri uri, String selection, String[] selectionArgs)
- {
- // TODO Auto-generated method stub
- return 0;
- }
- @Override
- public int update(Uri uri, ContentValues values, String selection,
- String[] selectionArgs)
- {
- // TODO Auto-generated method stub
- return 0;
- }
- }
这样,一个虽简单但可行的内容提供者就创建好了,现在我们只需在AndroidManifest文件中注册它。
- <provider android:name="com.whathecode.provider.MemberProvider"
- android:authorities="com.whathecode.contentproviderdemo.member">
- </provider>
接下来,运行这个程序,将我们刚才定义的ContentProvider部署到模拟器。
然后,我们建立另外一个程序测试这个内容提供者是否真的工作正常。
下面是另外一个程序的代码:
我们需要另外一个类进行访问ContentProvider提供的数据。
这个类就是ContentResolver,它提供了和ContentProvider一样的CRUD方法。
方便我们查询数据。
- package com.whathecode.contentprovidertest;
- import android.app.Activity;
- import android.content.BroadcastReceiver;
- import android.content.ContentResolver;
- import android.content.Context;
- import android.content.Intent;
- import android.content.IntentFilter;
- import android.net.Uri;
- import android.os.Bundle;
- import android.view.View;
- import android.widget.Toast;
- public class MainActivity extends Activity
- {
- private BroadcastReceiver receiver;
- @Override
- protected void onCreate(Bundle savedInstanceState)
- {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.activity_main);
- //创建一个广播接受者用于接收MemberProvider发出的广播
- receiver = new BroadcastReceiver()
- {
- @Override
- public void onReceive(Context context, Intent intent)
- {
- /**
- * 当广播被接收到的时候Toast提示用户接收到的信息
- */
- Toast.makeText(getBaseContext(),
- "收到的信息" + intent.getStringExtra("MemberProvider"),
- Toast.LENGTH_SHORT).show();
- }
- };
- }
- @Override
- protected void onResume()
- {
- super.onResume();
- //注册广播接受者
- registerReceiver(receiver, new IntentFilter("com.contentprovider.execquery"));
- }
- public void onClick(View view)
- {
- /**
- * 获取ContentResolver实例访问ContentProvider
- */
- ContentResolver resolver = getContentResolver();
- Uri uri = Uri
- .parse("content://com.whathecode.contentproviderdemo.member/name");
- resolver.query(uri, null, null, null, null);
- }
- @Override
- protected void onPause()
- {
- super.onPause();
- //取消注册广播接受者
- unregisterReceiver(receiver);
- }
- }
运行效果:
如果Toast运行证明MemberProvider中的query方法被成功执行
使用ContentProvider进行应用程序间的数据交互的更多相关文章
- contentprovider提供程序间共享数据的统一接口
contentprovider提供程序间共享数据的统一接口
- iPhone应用程序间传递数据
前一篇简单的介绍了iPhone应用程序间通信,主要是通过在被调用应用的Info.plist中加入URL方案,在应用中通过openUrl来实现程序的调用.而应用程序间的数据传递则可以更具url来实现,例 ...
- Windows窗体间的数据交互
轻松掌握Windows窗体间的数据交互 作者:郑佐 2004-04-05 Windows 窗体是用于 Microsoft Win ...
- View与Control间的数据交互
View与Control间的数据交互 1.ViewBag.Name ="Name1" 2.ViewData["VD"] = "view data&qu ...
- linux 共享内存shm_open实现进程间大数据交互
linux 共享内存shm_open实现进程间大数据交互 read.c #include <sys/types.h> #include <sys/stat.h> #includ ...
- iOS应用程序间共享数据
我们知道iOS由于沙盒的存在,应用程序不能越过自己的区域去访问别的存储空间的内容,不过可能有许多场景我们需要在应用程序之间共享数据,比如多个应用共用用户名密码进行登录等.虽然我们不能直接通过文件系统来 ...
- python的进程间的数据交互
#先来看下如何实现多进程 # multiprocessing 这个是python的多进程的模块,我们会用到这个模块的很多方法 from multiprocessing import Process i ...
- 【python】-- 多进程的基本语法 、进程间数据交互与共享、进程锁和进程池的使用
多进程 进程之间是相互独立的,python是启动进程的时候,是启动的是原生进程.进程是没有GIL锁的,而且不存在锁的概念,进程之间的数据式不能共享的,而线程是可以的. 1.进程的定义 用mulipro ...
- Hybrid小程序混合开发之路 - 数据交互
HTML+CSS是历史悠久.超高自由度.控制精准.表现能力极强.编码简单.学习门槛超低.真跨平台的一种UI界面开发方式. 本文介绍的是微信小程序和H5混合开发的一种数据交互方式. 很多应用在原生界面中 ...
随机推荐
- To create my first app in iOS with Xcode(在Xcode创建我的第一个iOS app )
To create my first app in iOS create the project. In the welcome window, click “Create a new Xcode p ...
- memcached在windows下多实例并存
文章来源:http://blog.csdn.net/xingxing513234072/article/details/39343999 memcached.exe的-d install命令安装时其他 ...
- arc如何破循环或交叉引用
IOS两种常见的循环引用: 1,两个类之间互相定义对方的引用 如下: //ARC code @interface A : NSObject @property (nonatomic,strong) B ...
- NET Core中实现一个Token base的身份认证
NET Core中实现一个Token base的身份认证 注:本文提到的代码示例下载地址> How to achieve a bearer token authentication and au ...
- (转)linux下vi命令大全
http://www.cnblogs.com/88999660/articles/1581524.html 进入vi的命令 vi filename :打开或新建文件,并将光标置于第一行首 vi +n ...
- 怎么实现ZBrush中Alt键和Shift键的灵活运用
ZBrush是一个数字雕刻和绘画软件,它以强大的功能和直观的工作流程彻底改变了整个三维雕刻行业.在一个简洁的界面中,ZBrush为当代数字艺术家提供了世界上最先进的工具.利用快捷键能使操作更快捷高效, ...
- jquery.roundabout.js实现3D图片层叠旋转木马切换
最近项目中需要实现3D图片层叠旋转木马切换的效果,于是用到了jquery.roundabout.js. 兼容性如图: html结构代码: <div id="featured-area& ...
- u3d_shader_surface_shader_1
http://docs.unity3d.com/Manual/SL-SurfaceShaders.html 一:surface shader是啥 Writing shaders that intera ...
- session跨域和ajax跨域名
后台跨域和ajax跨域名: 后台跨域: www.baidu.com 主域名(一级域名一般以www开头) news.baidu.com 二级域名 (a.test.com和b.test.com有相 ...
- Cornerstone 哪些错误
1.Unable to connect to a repository at URl.............,The operation could not be completed 说明无法连接的 ...