Android中ContentProvider和ContentResolver使用入门

在Android中,我们的应用有的时候需要对外提供数据接口,可以有如下几种方法:1)AIDL 2)Broadcast 3)ContentProvider。
使用AIDL需要我们编写AIDL接口以及实现,而且对方也要有相应的接口描述,有点麻烦;使用Broadcast,我们不需要任何接口描述,只要协议文档就可以了,但是有点不好就是,这种方式不直接而且是异步的;使用ContentProvider我们不需要接口描述,只需要知道协议,同时这种方式是同步的,使用方便。下面是ContentProvider实现:
/** */ /**
 * 
 
*/

package  com.backgroundservice;

import  android.content.ContentProvider;
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.util.Log;

/** */ /**
 * TODO
 * 
 * 
@author tianlu
 * 
@version 1.0 Create At : 2010-2-18 下午01:58:39
 
*/

public   class  TestContentProvider  extends  ContentProvider  {
    
private SQLiteDatabase mDb;
    
private DatabaseHelper mDbHelper = null;
    
private static final String DATABASE_NAME = "rssitems.db";
    
private static final String DATABASE_TABLE_NAME = "rssItems";
    
private static final int DB_VERSION = 1;
    
private static final int ALL_MESSAGES = 1;
    
private static final int SPECIFIC_MESSAGE = 2;

    
// Set up our URL matchers to help us determine what an
    
// incoming URI parameter is.
    private static final UriMatcher URI_MATCHER;
    
static {
        URI_MATCHER 
= new UriMatcher(UriMatcher.NO_MATCH);
        URI_MATCHER.addURI(
"test""item", ALL_MESSAGES);
        URI_MATCHER.addURI(
"test""item/#", SPECIFIC_MESSAGE);
    }


    
// Here's the public URI used to query for RSS items.
    public static final Uri CONTENT_URI = Uri
            .parse(
"content://test/item");

    
// Here are our column name constants, used to query for field values.
    public static final String ID = "_id";
    
public static final String NAME = "NAME";
    
public static final String VALUE = "VALUE";
    
public static final String DEFAULT_SORT_ORDER = ID + " DESC";

    
private static class DatabaseHelper extends AbstractDatabaseHelper {

        @Override
        
protected String[] createDBTables() {
            
// TODO Auto-generated method stub
            String sql = "CREATE TABLE " + DATABASE_TABLE_NAME + "(" + ID
                    
+ " INTEGER PRIMARY KEY AUTOINCREMENT, " + NAME + " TEXT,"
                    
+ VALUE + " TEXT);";
            
return new String[] { sql };
        }


        @Override
        
protected String[] dropDBTables() {
            
// TODO Auto-generated method stub
            return null;
        }


        @Override
        
protected String getDatabaseName() {
            
// TODO Auto-generated method stub
            return DATABASE_NAME;
        }


        @Override
        
protected int getDatabaseVersion() {
            
// TODO Auto-generated method stub
            return DB_VERSION;
        }


        @Override
        
protected String getTag() {
            
// TODO Auto-generated method stub
            return TestContentProvider.class.getSimpleName();
        }


    }


    
/** *//**
     * 
     
*/

    
public TestContentProvider() {
        
// TODO Auto-generated constructor stub
        
    }


    
/**//*
     * (non-Javadoc)
     * 
     * @see android.content.ContentProvider#delete(android.net.Uri,
     * java.lang.String, java.lang.String[])
     
*/

    @Override
    
public int delete(Uri uri, String selection, String[] selectionArgs) {
        
// NOTE Argument checking code omitted. Check your parameters!
        int rowCount = mDb.delete(DATABASE_TABLE_NAME, selection, selectionArgs);

        
// Notify any listeners and return the deleted row count.
        getContext().getContentResolver().notifyChange(uri, null);
        
return rowCount;
    }


    
/**//*
     * (non-Javadoc)
     * 
     * @see android.content.ContentProvider#getType(android.net.Uri)
     
*/

    @Override
    
public String getType(Uri uri) {
        
switch (URI_MATCHER.match(uri)) {
        
case ALL_MESSAGES:
            
return "vnd.android.cursor.dir/rssitem"// List of items.
        case SPECIFIC_MESSAGE:
            
return "vnd.android.cursor.item/rssitem"// Specific item.
        default:
            
return null;
        }

    }


    
/**//*
     * (non-Javadoc)
     * 
     * @see android.content.ContentProvider#insert(android.net.Uri,
     * android.content.ContentValues)
     
*/

    @Override
    
public Uri insert(Uri uri, ContentValues values) {
        
// NOTE Argument checking code omitted. Check your parameters! Check that
        
// your row addition request succeeded!

       
long rowId = -1;
       rowId 
= mDb.insert(DATABASE_TABLE_NAME, NAME, values);
       Uri newUri 
= Uri.withAppendedPath(CONTENT_URI, ""+rowId);
       Log.i(
"TestContentProvider""saved a record " + rowId + " " + newUri);
       
// Notify any listeners and return the URI of the new row.
       getContext().getContentResolver().notifyChange(CONTENT_URI, null);
       
return newUri;
    }


    
/**//*
     * (non-Javadoc)
     * 
     * @see android.content.ContentProvider#onCreate()
     
*/

    @Override
    
public boolean onCreate() {
        
// TODO Auto-generated method stub
        try
        
{
            mDbHelper 
= new DatabaseHelper();
            mDbHelper.open(getContext());
            mDb 
= mDbHelper.getMDb();
        }
catch(Exception e){
            e.printStackTrace();
        }

        
return true;
    }


    
/**//*
     * (non-Javadoc)
     * 
     * @see android.content.ContentProvider#query(android.net.Uri,
     * java.lang.String[], java.lang.String, java.lang.String[],
     * java.lang.String)
     
*/

    
public Cursor query(Uri uri, String[] projection, String selection,
            String[] selectionArgs, String sortOrder) 
{
        
// We won't bother checking the validity of params here, but you should!

        
// SQLiteQueryBuilder is the helper class that creates the
        
// proper SQL syntax for us.
        SQLiteQueryBuilder qBuilder = new SQLiteQueryBuilder();

        
// Set the table we're querying.
        qBuilder.setTables(DATABASE_TABLE_NAME);

        
// If the query ends in a specific record number, we're
        
// being asked for a specific record, so set the
        
// WHERE clause in our query.
        if((URI_MATCHER.match(uri)) == SPECIFIC_MESSAGE){
            qBuilder.appendWhere(
"_id=" + uri.getLastPathSegment());
            Log.i(
"TestContentProvider""_id=" +  uri.getLastPathSegment());
        }



        
// Make the query.
        Cursor c = qBuilder.query(mDb,
                projection,
                selection,
                selectionArgs,
                
null,
                
null,
                sortOrder);
        Log.i(
"TestContentProvider""get records");
        c.setNotificationUri(getContext().getContentResolver(), uri);
        
return c;
    }


    
/**//*
     * (non-Javadoc)
     * 
     * @see android.content.ContentProvider#update(android.net.Uri,
     * android.content.ContentValues, java.lang.String, java.lang.String[])
     
*/

    @Override
    
public int update(Uri uri, ContentValues values, String selection,
            String[] selectionArgs) 
{
        
// NOTE Argument checking code omitted. Check your parameters!
        int updateCount = mDb.update(DATABASE_TABLE_NAME, values, selection, selectionArgs);

        
// Notify any listeners and return the updated row count.
        getContext().getContentResolver().notifyChange(uri, null);
        
return updateCount;
    }


}

配置文件如下:
         < provider  android:name ="TestContentProvider"
            android:authorities
="test" >
        
</ provider >
在客户端中可以使用如下方法进行调用:
                ContentValues values  =   new  ContentValues();
                values.put(TestContentProvider.NAME, 
" testname1 " );
                values.put(TestContentProvider.VALUE, 
" testvalu1e " );
                Uri newAddUri 
=  TestActivity. this .getContentResolver().insert(TestContentProvider.CONTENT_URI, values);
                Cursor c 
=  TestActivity. this .managedQuery(newAddUri,  new  String[] {TestContentProvider.NAME} null null null );
                Log.i(
" TestActivity " ""   +  c.getCount());
                
if (c.moveToNext())
                
{
                    Log.i(
"TestActivity", c.getString(0));
                }

上面的代码是先进行插入,然后进行查询并打印。就是如此简单,所有的应用如果需要都可以对外方便的提供数据接口,同时其他应用也可以很方便的进行调用。

 

 

 

TrackBack:http://www.blogjava.net/TiGERTiAN/archive/2010/02/18/313403.html

转载于:https://www.cnblogs.com/hdjjun/archive/2010/06/02/1749863.html

评论将由博主筛选后显示,对所有人可见 | 还能输入1000个字符 “速评一下”
限时福利1:原价 129 元,最后2天仅需 69 元!后天涨价至98元 限时福利2:购课进答疑群专享柳峰(刘运强)老师答疑服务 限时福利3:购课添加助教领取价值 800 元的编程大礼包 为什么需要掌握高性能的MySQL实战? 由于互联网产品用户量大、高并发请求场景多,因此对MySQL的性能、可用性、扩展性都提出了很高的要求。使用MySQL解决大量数据以及高并发请求已经是程序员的必备技能,也是衡量一个程序员能力和薪资的标准之一。 为了让大家快速系统了解高性能MySQL核心知识全貌,我为你总结了「高性能 MySQL 知识框架图」,帮你梳理学习重点,建议收藏! 【课程设计】 课程分为四大篇章,将为你建立完整的 MySQL 知识体系,同时将重点讲解 MySQL 底层运行原理、数据库的性能调优、高并发、海量业务处理、面试解析等。 一、性能优化篇: 主要包括经典 MySQL 问题剖析、索引底层原理和事务与锁机制。通过深入理解 MySQL 的索引结构 B+Tree ,学员能够从根本上弄懂为什么有些 SQL 走索引、有些不走索引,从而彻底掌握索引的使用和优化技巧,能够避开很多实战遇到的“坑”。 二、MySQL 8.0新特性篇: 主要包括窗口函数和通用表表达式。企业的许多报表统计需求,如果不采用窗口函数,用普通的 SQL 语句是很难实现的。 三、高性能架构篇: 主要包括主从复制和读写分离。在企业的生产环境,很少采用单台MySQL节点的情况,因为一旦单个节点发生故障,整个系统都不可用,后果往往不堪设想,因此掌握高可用架构的实现是非常有必要的。 四、面试篇: 程序员获得工作的第一步,就是高效的准备面试,面试篇主要从知识点回顾总结的角度出发,结合程序员面试高频MySQL问题精讲精练,帮助程序员吊打面试官,获得心仪的工作机会。
©️2020 CSDN 皮肤主题: 大白 设计师:CSDN官方博客 返回首页