转载

SQLite数据库与Contentprovider

ContentProvider

在创建ContentProvider时,需要首先使用数据库、文件系统或网络实现底层存储功能,

然后在继承ContentProvider的类中实现基本数据操作的接口函数,包括添加、删除、查找和更新等功能。

调用者不能够直接调用ContentProvider的接口函数,而需要使用ContentResolver对象,

通过URI间接调用ContentProvider。下图是ContentProvider调用关系。

SQLite数据库与Contentprovider

URI

URI是通用资源标志符(Uniform Resource Identifier),用来定位任何远程或本地的可用资源

ContentProvider使用的URI语法结构如下

 content://<authority>/<data_path>/<id> 

content://是通用前缀,表示该URI用于ContentProvider定位资源,无需修改。

<authority>是授权者名称,用来确定具体由哪一个ContentProvider提供资源。因此,一般<authority>都由类的小写全称组成,以保证唯一性。

<data_path>是数据路径,用来确定请求的是哪个数据集。

例如:

 content://edu.hrbeu.peopleprovider/people/3 

可以省略id(/3)部分那么意味着整个数据。

UriMatcher:

在新构造的ContentProvider类中,通过构造一个UriMatcher,判断URI是单条数据还是多条数据。

public void  addURI  (String authority, String path, int code)

authority表示匹配的授权者名称

path表示数据路径

#可以代表任何数字 ( content://<authority>/<data_path>/#

code表示返回代码 uriMatcher.match(uri))的返回值

注册ContentProvider

 <provider android:name = ".PeopleProvider" android:authorities = "edu.hrbeu.peopleprovider"/>  

实例:

ContentProvider一般用于两个不同的进程之间的数据共享。

  1. 假设我们有一个新的工程(app),在此工程中创建一个people.db数据库,然后通过自定义了一个ContentProvider来共享数据库中的data。
  2. 我们可以通过注册provider时用到的authority在配合db path之类的来连接( content://<authority>/<data_path>/# )读取内容提供者(不同进程)的数据。

首先是步骤1:

*只要在AndroidManifast中注册provider就会执行对应的provider类。无需再MainActivity中调用或无需直接调用自定义的new provider。

即系统自动会加载调用PeopleProvider类。

 <provider android:name = ".PeopleProvider" android:authorities = "edu.hrbeu.peopleprovider"/>  

继承ContentProvider时代码如下:

 import android.content.*; import android.database.Cursor; import android.net.Uri;   public class PeopleProvider extends ContentProvider{     @Override     public int delete(Uri uri, String selection, String[] selectionArgs) {         // TODO Auto-generated method stub         return 0;     }      @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 boolean onCreate() {         // TODO Auto-generated method stub         return false;     }          @Override     public Cursor query(Uri uri, String[] projection, String selection,             String[] selectionArgs, String sortOrder) {         // TODO Auto-generated method stub         return null;     }       @Override     public int update(Uri uri, ContentValues values, String selection,             String[] selectionArgs) {         // TODO Auto-generated method stub         return 0;     } } 

类似数据库操作。可以这么理解,相对来说好理解。

开始贴代码。。。

 package edu.hrbeu.contentproviderdemo;   import android.content.ContentProvider; import android.content.ContentUris; import android.content.ContentValues; import android.content.Context; import android.content.UriMatcher; import android.database.Cursor; import android.database.SQLException; import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteDatabase.CursorFactory; import android.database.sqlite.SQLiteOpenHelper; import android.database.sqlite.SQLiteQueryBuilder; import android.net.Uri;  public class PeopleProvider extends ContentProvider {          private static final String DB_NAME = "people.db";     private static final String DB_TABLE = "peopleinfo";     private static final int DB_VERSION = 1;          private SQLiteDatabase db;     private DBOpenHelper dbOpenHelper;          private static final int MULTIPLE_PEOPLE = 1;     private static final int SINGLE_PEOPLE = 2;     private static final UriMatcher uriMatcher;     static {          uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);          uriMatcher.addURI(People.AUTHORITY, People.PATH_MULTIPLE, MULTIPLE_PEOPLE);          uriMatcher.addURI(People.AUTHORITY, People.PATH_SINGLE, SINGLE_PEOPLE);     }      @Override     public boolean onCreate() {         // TODO Auto-generated method stub         Context context = getContext();         dbOpenHelper = new DBOpenHelper(context, DB_NAME, null, DB_VERSION);         db = dbOpenHelper.getWritableDatabase();           if (db == null)             return false;         else              return true;          }      @Override     public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {         // TODO Auto-generated method stub         SQLiteQueryBuilder qb = new SQLiteQueryBuilder();         qb.setTables(DB_TABLE);         switch(uriMatcher.match(uri)){             case SINGLE_PEOPLE:                 qb.appendWhere(People.KEY_ID + "=" + uri.getPathSegments().get(1));                 break;             default:                 break;         }         Cursor cursor = qb.query(db,                  projection,                  selection,                  selectionArgs,                  null,                  null,                  sortOrder);         cursor.setNotificationUri(getContext().getContentResolver(), uri);         return cursor;      }      @Override     public String getType(Uri uri) {         // TODO Auto-generated method stub         switch(uriMatcher.match(uri)){         case MULTIPLE_PEOPLE:     return People.MINE_TYPE_MULTIPLE;         case SINGLE_PEOPLE:     return People.MINE_TYPE_SINGLE;         default:                 throw new IllegalArgumentException("Unkown uri:"+uri); }      }      @Override     public Uri insert(Uri uri, ContentValues values) {         // TODO Auto-generated method stub         long id = db.insert(DB_TABLE, null, values);         if ( id > 0 ){             Uri newUri = ContentUris.withAppendedId(People.CONTENT_URI, id);             getContext().getContentResolver().notifyChange(newUri, null);             return newUri;         }         throw new SQLException("Failed to insert row into " + uri);      }      @Override     public int delete(Uri uri, String selection, String[] selectionArgs) {         // TODO Auto-generated method stub         int count = 0;         switch(uriMatcher.match(uri)){     case MULTIPLE_PEOPLE:            count = db.delete(DB_TABLE, selection, selectionArgs);            break;                   case SINGLE_PEOPLE:            String segment = uri.getPathSegments().get(1);                          count = db.delete(DB_TABLE, People.KEY_ID + "=" + segment, selectionArgs);            break;    default:            throw new IllegalArgumentException("Unsupported URI:" + uri); }         getContext().getContentResolver().notifyChange(uri, null);          return count;      }      @Override     public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {         // TODO Auto-generated method stub         int count;         switch(uriMatcher.match(uri)){                  case MULTIPLE_PEOPLE:                         count = db.update(DB_TABLE, values, selection, selectionArgs);                         break;                                      case SINGLE_PEOPLE:                                              String segment = uri.getPathSegments().get(1);                         count = db.update(DB_TABLE, values, People.KEY_ID+"="+segment, selectionArgs);                            break;                                      default:             throw new IllegalArgumentException("Unknow URI:" + uri);              }         getContext().getContentResolver().notifyChange(uri, null);         return count;      }            private static class DBOpenHelper extends SQLiteOpenHelper {                      public DBOpenHelper(Context context, String name, CursorFactory factory, int version) {             super(context, name, factory, version);           }           private static final String DB_CREATE = "create table " +                      DB_TABLE + " (" + People.KEY_ID + " integer primary key autoincrement, " +                            People.KEY_NAME+ " text not null, " + People.KEY_AGE+ " integer," + People.KEY_HEIGHT + " float);";         @Override         public void onCreate(SQLiteDatabase _db) {             // TODO Auto-generated method stub             _db.execSQL(DB_CREATE);         }         @Override         public void onUpgrade(SQLiteDatabase _db, int oldVersion, int newVersion) {             // TODO Auto-generated method stub             _db.execSQL("DROP TABLE IF EXISTS " + DB_TABLE);                onCreate(_db);          }        }      } 
 package edu.hrbeu.contentproviderdemo; import android.net.Uri;   public class People{          public static final String MIME_DIR_PREFIX = "vnd.android.cursor.dir";     public static final String MIME_ITEM_PREFIX = "vnd.android.cursor.item";     public static final String MINE_ITEM = "vnd.hrbeu.people";          public static final String MINE_TYPE_SINGLE = MIME_ITEM_PREFIX + "/" + MINE_ITEM;     public static final String MINE_TYPE_MULTIPLE = MIME_DIR_PREFIX + "/" + MINE_ITEM;     public static final String AUTHORITY = "edu.hrbeu.peopleprovider";     public static final String PATH_SINGLE = "people/#";     public static final String PATH_MULTIPLE = "people";     public static final String CONTENT_URI_STRING = "content://" + AUTHORITY + "/" + PATH_MULTIPLE;     public static final Uri  CONTENT_URI = Uri.parse(CONTENT_URI_STRING);           public static final String KEY_ID = "_id";     public static final String KEY_NAME = "name";     public static final String KEY_AGE = "age";     public static final String KEY_HEIGHT = "height"; } 

MainActivity是空的。。。不贴出来了。

运行结果没有任何内容,因为仅是添加了一个provider。

SQLite数据库与Contentprovider

看一下步骤2:

在另一个App中调用此ContentProvider。

无需再AndroidManifast中注册provider。

只需对应步骤1中的People类里的静态变量是完全匹配的就是可以了。

也就是说URI需要与我们自定义的ContentProvider保持一致。

 package edu.hrbeu.contentresolverdemo; import android.net.Uri;   public class People{          public static final String MIME_DIR_PREFIX = "vnd.android.cursor.dir";     public static final String MIME_ITEM_PREFIX = "vnd.android.cursor.item";     public static final String MINE_ITEM = "vnd.hrbeu.people";          public static final String MINE_TYPE_SINGLE = MIME_ITEM_PREFIX + "/" + MINE_ITEM;     public static final String MINE_TYPE_MULTIPLE = MIME_DIR_PREFIX + "/" + MINE_ITEM;     public static final String AUTHORITY = "edu.hrbeu.peopleprovider";     public static final String PATH_SINGLE = "people/#";     public static final String PATH_MULTIPLE = "people";     public static final String CONTENT_URI_STRING = "content://" + AUTHORITY + "/" + PATH_MULTIPLE;     public static final Uri  CONTENT_URI = Uri.parse(CONTENT_URI_STRING);           public static final String KEY_ID = "_id";     public static final String KEY_NAME = "name";     public static final String KEY_AGE = "age";     public static final String KEY_HEIGHT = "height"; } 

操作Contentpriver提供的数据我们需要用到ContentResolver:

 package edu.hrbeu.contentresolverdemo;  import android.app.Activity; import android.os.Bundle; import android.view.Menu; import android.view.MenuItem; import android.content.ContentResolver; import android.content.ContentValues; import android.database.Cursor; import android.net.Uri; import android.view.View; import android.view.View.OnClickListener; import android.widget.Button; import android.widget.EditText; import android.widget.TextView;  public class ContentResolverDemo extends Activity {      private EditText nameText;     private EditText ageText;     private EditText heightText;     private EditText idEntry;      private TextView labelView;     private TextView displayView;      private ContentResolver resolver;      @Override     protected void onCreate(Bundle savedInstanceState) {         super.onCreate(savedInstanceState);         setContentView(R.layout.activity_content_resolver_demo);         nameText = (EditText) findViewById(R.id.name);         ageText = (EditText) findViewById(R.id.age);         heightText = (EditText) findViewById(R.id.hight);         idEntry = (EditText) findViewById(R.id.id);          labelView = (TextView) findViewById(R.id.label);         displayView = (TextView) findViewById(R.id.display);         Button addButton = (Button) findViewById(R.id.button1);         Button queryAllButton = (Button) findViewById(R.id.button2);         Button clearButton = (Button) findViewById(R.id.button3);         Button queryButton = (Button) findViewById(R.id.button6);         Button deleteButton = (Button) findViewById(R.id.button5);         Button updateButton = (Button) findViewById(R.id.button7);          resolver = this.getContentResolver();         addButton.setOnClickListener(new OnClickListener() {              @Override             public void onClick(View v) {                 // TODO Auto-generated method stub                 ContentValues values = new ContentValues();                  values.put(People.KEY_NAME, nameText.getText().toString());                 values.put(People.KEY_AGE,                         Integer.parseInt(ageText.getText().toString()));                 values.put(People.KEY_HEIGHT,                         Float.parseFloat(heightText.getText().toString()));                  Uri newUri = resolver.insert(People.CONTENT_URI, values);                 labelView.setText("添加成功,URI:" + newUri);              }         });         queryAllButton.setOnClickListener(new OnClickListener() {              @Override             public void onClick(View v) {                 // TODO Auto-generated method stub                 Cursor cursor = resolver.query(People.CONTENT_URI,                         new String[] { People.KEY_ID, People.KEY_NAME,                                 People.KEY_AGE, People.KEY_HEIGHT }, null,                         null, null);                 if (cursor == null) {                     labelView.setText("数据库中没有数据");                     return;                 }                 labelView.setText("数据库:" + String.valueOf(cursor.getCount())                         + "条记录");                  String msg = "";                 if (cursor.moveToFirst()) {                     do {                         msg += "ID:"                                 + cursor.getInt(cursor                                         .getColumnIndex(People.KEY_ID)) + ",";                         msg += "姓名:"                                 + cursor.getString(cursor                                         .getColumnIndex(People.KEY_NAME)) + ",";                         msg += "年龄:"                                 + cursor.getInt(cursor                                         .getColumnIndex(People.KEY_AGE)) + ", ";                         msg += "身高:"                                 + cursor.getFloat(cursor                                         .getColumnIndex(People.KEY_HEIGHT))                                 + "/n";                     } while (cursor.moveToNext());                 }                  displayView.setText(msg);              }         });          clearButton.setOnClickListener(new OnClickListener() {              @Override             public void onClick(View v) {                 // TODO Auto-generated method stub                 displayView.setText("");             }         });          queryButton.setOnClickListener(new OnClickListener() {              @Override             public void onClick(View v) {                 // TODO Auto-generated method stub                 Uri uri = Uri.parse(People.CONTENT_URI_STRING + "/"                         + idEntry.getText().toString());                 Cursor cursor = resolver.query(uri, new String[] {                         People.KEY_ID, People.KEY_NAME, People.KEY_AGE,                         People.KEY_HEIGHT }, null, null, null);                 if (cursor == null) {                     labelView.setText("数据库中没有数据");                     return;                 }                  String msg = "";                 if (cursor.moveToFirst()) {                     msg += "ID:"                             + cursor.getInt(cursor                                     .getColumnIndex(People.KEY_ID)) + ",";                     msg += "姓名:"                             + cursor.getString(cursor                                     .getColumnIndex(People.KEY_NAME)) + ",";                     msg += "年龄:"                             + cursor.getInt(cursor                                     .getColumnIndex(People.KEY_AGE)) + ", ";                     msg += "身高:"                             + cursor.getFloat(cursor                                     .getColumnIndex(People.KEY_HEIGHT)) + "/n";                 }                  labelView.setText("数据库:");                 displayView.setText(msg);              }         });         deleteButton.setOnClickListener(new OnClickListener() {              @Override             public void onClick(View v) {                 // TODO Auto-generated method stub                 Uri uri = Uri.parse(People.CONTENT_URI_STRING + "/"                         + idEntry.getText().toString());                 int result = resolver.delete(uri, null, null);                 String msg = "删除ID为" + idEntry.getText().toString() + "的数据"                         + (result > 0 ? "成功" : "失败");                 labelView.setText(msg);             }         });          updateButton.setOnClickListener(new OnClickListener() {              @Override             public void onClick(View v) {                 // TODO Auto-generated method stub                 ContentValues values = new ContentValues();                 values.put(People.KEY_NAME, nameText.getText().toString());                 values.put(People.KEY_AGE,                         Integer.parseInt(ageText.getText().toString()));                 values.put(People.KEY_HEIGHT,                         Float.parseFloat(heightText.getText().toString()));                  Uri uri = Uri.parse(People.CONTENT_URI_STRING + "/"                         + idEntry.getText().toString());                 int result = resolver.update(uri, values, null, null);                  String msg = "更新ID为" + idEntry.getText().toString() + "的数据"                         + (result > 0 ? "成功" : "失败");                 labelView.setText(msg);              }         });     }      @Override     public boolean onCreateOptionsMenu(Menu menu) {         // Inflate the menu; this adds items to the action bar if it is present.         getMenuInflater().inflate(R.menu.content_resolver_demo, menu);         return true;     }      @Override     public boolean onOptionsItemSelected(MenuItem item) {         // Handle action bar item clicks here. The action bar will         // automatically handle clicks on the Home/Up button, so long         // as you specify a parent activity in AndroidManifest.xml.         int id = item.getItemId();         if (id == R.id.action_settings) {             return true;         }         return super.onOptionsItemSelected(item);     } } 

事成相识的布局文件也附上:

 <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:tools="http://schemas.android.com/tools"     android:layout_width="match_parent"     android:layout_height="match_parent"     android:paddingBottom="@dimen/activity_vertical_margin"     android:paddingLeft="@dimen/activity_horizontal_margin"     android:paddingRight="@dimen/activity_horizontal_margin"     android:paddingTop="@dimen/activity_vertical_margin"     tools:context="edu.hrbeu.contentresolverdemo.ContentResolverDemo" >      <TextView android:id="@+id/Username"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:text="用户名:">     </TextView>      <EditText         android:id="@+id/name"         android:layout_width="fill_parent"         android:layout_height="wrap_content"         android:layout_below="@id/Username" >      </EditText>      <TextView android:id="@+id/Userage"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:layout_below="@id/name"         android:text="年龄:">     </TextView>     <EditText android:id="@+id/age"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:layout_below="@id/Userage">     </EditText>           <TextView android:id="@+id/Userhight"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:layout_below="@id/age"         android:text="身高:">     </TextView>     <EditText android:id="@+id/hight"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:layout_below="@id/Userhight">     </EditText>      <Button         android:id="@+id/button2"         android:layout_width="wrap_content"         android:layout_height="wrap_content"         android:layout_alignBaseline="@+id/button1"         android:layout_alignBottom="@+id/button1"         android:layout_centerHorizontal="true"         android:text="全部显示" />      <Button         android:id="@+id/button3"         android:layout_width="wrap_content"         android:layout_height="wrap_content"         android:layout_alignBaseline="@+id/button2"         android:layout_alignBottom="@+id/button2"         android:layout_alignRight="@+id/hight"         android:text="清除显示" />          <TextView android:id="@+id/Userid"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:layout_below="@id/button1"         android:text="ID:">     </TextView>     <EditText android:id="@+id/id"          android:layout_height="wrap_content"          android:layout_width="fill_parent"          android:layout_below="@id/Userid">     </EditText>      <Button         android:id="@+id/button6"         android:layout_width="wrap_content"         android:layout_height="wrap_content"         android:layout_alignBaseline="@+id/button5"         android:layout_alignBottom="@+id/button5"         android:layout_alignLeft="@+id/button2"         android:text="ID查询" />      <Button         android:id="@+id/button7"         android:layout_width="wrap_content"         android:layout_height="wrap_content"         android:layout_alignBaseline="@+id/button6"         android:layout_alignBottom="@+id/button6"         android:layout_alignLeft="@+id/button3"         android:text="ID更新" />      <Button         android:id="@+id/button1"         android:layout_width="wrap_content"         android:layout_height="wrap_content"         android:layout_below="@+id/hight"         android:text="添加数据" />      <Button         android:id="@+id/button5"         android:layout_width="wrap_content"         android:layout_height="wrap_content"         android:layout_alignLeft="@+id/id"         android:layout_below="@+id/id"         android:text="ID删除" />      <TextView         android:id="@+id/display"         android:layout_width="fill_parent"         android:layout_height="wrap_content"         android:layout_alignLeft="@+id/label"         android:layout_below="@+id/label"         android:layout_marginTop="23dp" />      <TextView         android:id="@+id/label"         android:layout_width="fill_parent"         android:layout_height="wrap_content"         android:layout_alignLeft="@+id/button5"         android:layout_below="@+id/button6"         android:layout_marginTop="14dp" />  </RelativeLayout> 

运行结果:

SQLite数据库与Contentprovider

原文  http://www.cnblogs.com/hongguang-kim/p/5631952.html
正文到此结束
Loading...