ContentProvider实现的是数据库操作的封装,并且可以实现数据之间的共享。也就是说,利用ContentProvider实现的数据存储可以在外部应用程序中访问的到。具体过程如下:

   一:扩展ContentProvider类提供数据访问接口

   扩展SQLiteOpenHelper类,提供数据库表的创建与更新(具体详情请见上一篇博文)

   注:这里建议数据库的表名,列名提取成全局静态常量,以方便后面的调用。

   这里创建的数据库为:quan.db。数据库表名为:user。列名有两项,分别为:_id(主键)和title。即

public class MySqlite extends SQLiteOpenHelper {
//数据库表名,列名提取成全局静态常量
    public static final String TABLE_NAME = "user";
    public static final String TABLE_TITLE = "title";
    public static final String TABLE_ID = "_id";
//构造方法
    public MySqlite(Context context) {
        super(context, "quan.db", null, 1);
    }
//数据库表的创建
    @Override
    public void onCreate(SQLiteDatabase db) {
        db.execSQL("create table " + TABLE_NAME + "(" + TABLE_ID
                + " integer primary key autoincrement," + TABLE_TITLE
                + " text not null)");
    }
//数据库表的更新
    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    }
}

   二:扩展ContentProvider抽象类,实现其中的六个抽象方法,完成对数据库操作的封装

   1:URI简介

   URI统一资源标识符,说白了,就是唯一标识资源的一个字串。同样的在ContentProvider中也需要唯一的一个字符串,标识提供数据的唯一性。也正是根据URI在Manifest.xml文件中的注册,外部应用程序才可能查找得到ContentProvider所提供的数据。

   具体的注册方式:

<provider
            android:name="继承自ContentProvider类的类名"
            android:authorities="包名.继承自ContentProvider类的类名" >
</provider>

   具体的URI格式:

public static final Uri URI = Uri.parse("content://包名.继承自Contentprovider的类名称(也就是注册中android:authorities的属性值)");

   注意:字符串中“content://”为固定格式。

   2:六个抽象方法及作用

   (1)onCreate():主要用来初始化使用到的工具,在ContentProvider对象创建之后就会被调用。比如继承自SQLiteOpenHelper类的对象的初始化,SQLiteDatabase中获得可读可写权限对象的初始化等。

   (2)query():返回类型为Cursor,通过对数据库具有可读权限对象的query方法,完成外部应用数据库关于表的查询操作。即:提供外部应用的从ContentProvider中获取数据。

   (3)insert():返回类型为Uri,通过对数据库具有可写权限对象的insert方法,完成数据库关于表的插入操作。即外部应用向ContentProvider中插入数据。

   (4)delete():返回类型为int,通过对数据库具有可写权限对象的delete方法,完成数据库中关于表的删除操作。即外部应用从ContentProvider中删除数据。

   (5)update():返回类型为int,通过对数据库具有可写权限对象的update方法,完成数据库中关于表的更新操作。即外部应用更新ContentProvider中的数据。

   (6)getType():用来标识ContentProvider中数据的类型。

   3:具体实现

public class MyCP extends ContentProvider {
    // 统一资源标识符
    public static final Uri URI = Uri
            .parse("content://com.example.day08_mycontentprovider.MyCP");
    // 声明数据库的创建与更新对象
    private MySqlite mySqlite;
    // 获得数据可读可写的对象
    private SQLiteDatabase dbWriter, dbReader;
    // 获得表名,列名等静态常量
    private static final String CP_TABLE_NAME = MySqlite.TABLE_NAME;
    private static final String CP_TABLE_TITLE = MySqlite.TABLE_TITLE;
    private static final String CP_TABLE_ID = MySqlite.TABLE_ID;
    @Override
    public boolean onCreate() {
        mySqlite = new MySqlite(getContext());// 数据库表的创建
        dbWriter = mySqlite.getWritableDatabase();// 实例化可读可写对象
        dbReader = mySqlite.getReadableDatabase();
        return true;
    }
    // 数据库关于表的查询
    @Override
    public Cursor query(Uri uri, String[] projection, String selection,
            String[] selectionArgs, String sortOrder) {
        return dbReader.query(CP_TABLE_NAME, projection, selection,
                selectionArgs, null, null, sortOrder);
    }
    // 数据库关于表的查插入
    @Override
    public Uri insert(Uri uri, ContentValues values) {
        dbWriter.insert(CP_TABLE_NAME, null, values);
        return uri;
    }
    // 数据库关于表的删除
    @Override
    public int delete(Uri uri, String selection, String[] selectionArgs) {
        return dbWriter.delete(CP_TABLE_NAME, selection, selectionArgs);
    }
    // 数据库关于表的更新
    @Override
    public int update(Uri uri, ContentValues values, String selection,
            String[] selectionArgs) {
        return dbWriter.update(CP_TABLE_NAME, values, selection, selectionArgs);
    }
    // 返回数据类型
    @Override
    public String getType(Uri uri) {
        return null;
    }
}

   三:内部应用程序的引用

   在应用程序中,通过getContentResolver()方法调用ContentProvider中的几个方法,完成数据中表的操作

public class MainActivity extends Activity {
    // 得到唯一标识ContentProvider的URI
    public Uri uri = MyCP.URI;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        addDB();
        // updateDB();
        // deleteDB();
        selectDB();
    }
    // 添加,通过getContentResolver()获得到ContentProvider的数据解析对象
    public void addDB() {
        ContentValues cv = new ContentValues();
        cv.put("title", "HelloWord");
        getContentResolver().insert(uri, cv);// 调用ContentProvider的insert方法,实现数据的添加
    }
    // 查询
    public void selectDB() {
        // 调用ContentProvider的query方法,实现数据的查询
        Cursor cursor = getContentResolver().query(uri, null, null, null, null);
        while (cursor.moveToNext()) {
            System.out
                    .println(cursor.getString(cursor.getColumnIndex("title")));
        }
    }
    // 修改
    public void updateDB() {
        // 调用ContentProvider的update方法,实现数据的修改
        ContentValues cv = new ContentValues();
        cv.put("title", "我改名了,我叫张三");
        getContentResolver().update(uri, cv, null, null);
    }
    // 删除
    public void deleteDB() {
        // 调用ContentProvider的delete方法,实现数据的删除
        getContentResolver().delete(uri, null, null);
    }
}

   四:外部应用程序的引用

   1:提取ContentProvider的唯一标识符URI为静态常量,其值为同上。

   2:通过getContentResolver()方法调用ContentProvider中的几个方法,完成数据中表的操作。

public class MainActivity extends Activity {
    //提取统一资源标识符URI,才能找得到ContentProvider所存储的数据
    public static final Uri URI = Uri.parse("content://com.example.day08_mycontentprovider.MyCP");
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        selectDB();//对方法的调用
    }
//通过getContentResolver()方法调用ContentProvider中的几个方法,完成数据中表的操作。
    public void selectDB(){
        Cursor cursor = getContentResolver().query(URI, null, null, null, null);
        while(cursor.moveToNext()){
            System.out.println(cursor.getString(cursor.getColumnIndex("title")));
        }
    }
}

  五:结果

  内部应用:数据库中的表存在于data/data/包名/database/***.db中,导出,运用SQLite Export查看存在于表中的数据

185311550.png

   外部应用:在控制台输出数据库中表的数据

08-31 10:31:39.158: I/System.out(285): HelloWord

   

  好声音开始了。。。 C_0012.gif