android存儲方式之ContentProvider存儲方式講解

android的五種存儲方式分別是:

1,SharedPreferences

2,file

3,sqlite

4,contentproviter

5,http

ContentProvider

註意:

大多數ContentProvider使用Android文件系統或者SQLite數據庫來保持數據,但是也可以以任何方式來存儲。

在清單文件中註冊一個自定義ContentProviter


        

重寫一個TestContentProvider類繼承ContentProviter

public class TestContentProvider extends ContentProvider {

    //這裡的AUTHORITY就是我們在AndroidManifest.xml中配置的authorities
    public static final String AUTHORITY = "com.lh.knowledge.contentprovider";

    //匹配成功後的匹配碼
    private static final int MATCH_ALL_CODE = 100;
    private static final int MATCH_ONE_CODE = 101;
    private static UriMatcher uriMatcher;//uri匹配器
    private Cursor cursor = null;//遊標

    List testBeanList = new ArrayList<>();

    @Override
    public boolean onCreate() {
        initData();
        //添加要匹配的uri,匹配不成功返回NO_MATCH(-1)
        uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
        /**
         * uriMatcher.addURI(authority, path, code); 其中
         * authority:主機名(用於唯一標示一個ContentProvider,這個需要和清單文件中的authorities屬性相同)
         * path:路徑路徑(可以用來表示我們要操作的數據,路徑的構建應根據業務而定)
         * code:返回值(用於匹配uri的時候,作為匹配成功的返回值)
         */
        uriMatcher.addURI(AUTHORITY, "student", MATCH_ALL_CODE);// 匹配記錄集合
        uriMatcher.addURI(AUTHORITY, "student/#", MATCH_ONE_CODE);// 匹配單條記錄
        return false;
    }

    private void initData() {
        TestBean testBean1 = new TestBean();
        testBean1.setId(1);
        testBean1.setName("aaa");
        testBean1.setPrice(5.2);
        testBean1.setSex(false);
        testBeanList.add(testBean1);

        TestBean testBean2 = new TestBean();
        testBean1.setId(2);
        testBean1.setName("bbb");
        testBean1.setPrice(6.2);
        testBean1.setSex(true);
        testBeanList.add(testBean2);

        TestBean testBean3 = new TestBean();
        testBean1.setId(3);
        testBean1.setName("ccc");
        testBean1.setPrice(0.2);
        testBean1.setSex(false);
        testBeanList.add(testBean3);
    }

    /**
     * @param uri
     * @param projection
     * @param selection
     * @param selectionArgs
     * @param sortOrder
     * @return
     */
    @Nullable
    @Override
    public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) {
        //這裡的查詢需要配合sqlite來使用
        return null;
    }

    @Nullable
    @Override
    public String getType(@NonNull Uri uri) {
        return null;
    }

    @Nullable
    @Override
    public Uri insert(@NonNull Uri uri, @Nullable ContentValues values) {
        int match = uriMatcher.match(uri);
        if (match != MATCH_ALL_CODE) {//這裡不能匹配集合,隻能匹配單個
            throw new IllegalArgumentException("Unkwon Uri:" + uri.toString());
        }
        //
        int indexId = values.getAsInteger("indexId");
        Uri insertUri = ContentUris.withAppendedId(uri, indexId);
        if (indexId > 0) {
            TestBean testBean = new TestBean();
            testBean.setId(indexId);
            testBean.setName("content provider userid " + indexId);
            testBeanList.add(testBean);
            return insertUri;
        }
        return null;
    }

    @Override
    public int delete(@NonNull Uri uri, @Nullable String selection, @Nullable String[] selectionArgs) {
        //匹配uri
        switch (uriMatcher.match(uri)) {
            case MATCH_ALL_CODE://集合
                int i = testBeanList.size();
                testBeanList.clear();
                return i;
            case MATCH_ONE_CODE://單個
                int postion = Integer.parseInt(selection);
                testBeanList.remove(postion);
                return 1;
            default://拋出異常,沒有匹配到uri
                //throw new IllegalArgumentException("Unkwon Uri:" + uri.toString());
                return 0;
        }
    }

    @Override
    public int update(@NonNull Uri uri, @Nullable ContentValues values, @Nullable String selection, @Nullable String[] selectionArgs) {
        int postion = Integer.parseInt(selection);
        if (postion > testBeanList.size() - 1) return 0;
        TestBean testBean = testBeanList.get(postion);
        if (testBean == null) return 0;
        String name = values.getAsString("name");
        testBean.setName(name);
        return 1;
    }
}

如何使用ContentProvider來存儲數據

public class ContentProviderActivity extends Activity {

    private ContentResolver contentResolver;
    private final Uri STUDENT_ALL_URI = Uri.parse("content://" + TestContentProvider.AUTHORITY + "/student");
    private final Uri STUDENT_ONE_URI = Uri.parse("content://" + TestContentProvider.AUTHORITY + "/student/#");

    private Handler handler = new Handler() {
        public void handleMessage(Message msg) {
            //這裡說明內容提供者的uri正確,隨機操作增刪改查
            /**
             * @param uri
             * @param projection
             * @param selection
             * @param selectionArgs
             * @param sortOrder
             * @return cursor
             */
            Cursor cursorAll = contentResolver.query(STUDENT_ALL_URI, null, null, null, null);
            //查詢userid為1的用戶
            Cursor cursorOne = contentResolver.query(STUDENT_ONE_URI, null, "1", null, null);
            //刪除userid為2的用戶,返回當前刪除條數
            int i = contentResolver.delete(STUDENT_ONE_URI, "2", null);
            //修改
            ContentValues contentValues = new ContentValues();
            contentValues.put("name", "test");
            int updateNumber = contentResolver.update(STUDENT_ONE_URI, contentValues, "1", null);
            //這裡的方法都與TestContentProvider中的方法相對應
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //獲得內容提供者解析器
        contentResolver = getContentResolver();
        //註冊內容觀察者
        contentResolver.registerContentObserver(STUDENT_ALL_URI, true, new PersonOberserver(handler));
    }

    /**
     * 觀察者,如果找到瞭當前uri的提供者,則會回調
     */
    public class PersonOberserver extends ContentObserver {

        private Handler handler;

        public PersonOberserver(Handler handler) {
            super(handler);
            this.handler = handler;
        }

        @Override
        public void onChange(boolean selfChange) {
            super.onChange(selfChange);
            //向handler發送消息,找到瞭當前的提供者
            Message msg = new Message();
            handler.sendMessage(msg);
        }

    }

ContentProviter能夠跨進程的存儲數據,通過調用相對應的方法能夠增、刪、改、查。

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *