Android ContentResolver 优化方案之 loader

Android读取系统联系人全攻略:ContentResolver原理、权限与实战 Android应用的数据隔离机制决定了应用无法直接访问其他应用或系统的私有数据库。为此,系统提供了ContentProvider作为数据提供方,通过ContentResolver这一统一入口进行跨进程数据交换。理解这一原理,是掌握系统联系人读取、媒体库访问、日历数据操作等技术的基础。基于此,以读取系统联系人为例,本文深入解析了ContactsContract的层次结构、运行时权限申请、批量查询优化及常见异常排查。通过ContentResolver和URI,开发者可以安全高效地获取联系人数据,避免直接操作数据 阅读详情
      在android 开发中耗时操作,尽量不要在UI线程中执行,而contentResolver 访问数据的方式是在主线程中,在数据量繁琐的时候,我们可以采用loader方式访问其他应用程序提供的数据,只需让,Activity,或者fragment 实现loaderCallBack 接口,实现其中的三个方法即可,需要注意的是,在执行完,onCreateLoader()方法之后,的返回值,将作为onLoadFinsh()方法的一个参数,类似异步操作中的doInbackGround ()以及onPostActivity()方法,在开启loader 的时候,getloaderManger().initLoader(int id,Bundle args,LoaderCallbacks<Cursor> callback)三个参数,代码中解释如下
    id A unique identifier for this loader. Can be whatever you want. Identifiers are scoped to a particular LoaderManager instance.
    args Optional arguments to supply to the loader at construction. If a loader already exists (a new one does not need to be created), this parameter will be ignored and the last arguments continue to be used.
    callback Interface the LoaderManager will call to report about changes in the state of the loader. Required.
    可见id 对此loader 起标识作用,假设你对数据库进行更改,需要重新加载数据库中的值,可调用 getLoaderManager().resetLoader(int id,Bundle args,LoaderCallbacks<Cursor> callback),三个参数,此时你需要使用,与之前相同id ,Bundle中可以给 onCreateLoader(int id, Bundle args) 方法传值 代码如下:
package com.example.loaderapp;

import android.app.Activity;

import android.app.LoaderManager.LoaderCallbacks;
import android.content.CursorLoader;
import android.content.Loader;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract;
import android.support.v4.widget.SimpleCursorAdapter;
import android.widget.ListView;
import android.widget.SearchView;
import android.widget.SearchView.OnQueryTextListener;

public class MainActivity extends Activity implements LoaderCallbacks<Cursor>{

    //Loader 加载
    /**
     * content resolver 在主线程中使用的
     */
    private ListView lv;

    private SimpleCursorAdapter adapter;

    private SearchView search;


    // 这个 uri 是针对 raw_contacts 和 data 两张表连接查询的  注意是 两张
    private Uri contactUri = ContactsContract.CommonDataKinds.Phone.CONTENT_URI;    

    private String[] columns = {"_id","display_name","raw_contact_id","data1"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        lv = (ListView) findViewById(R.id.lv);
        search = (SearchView) findViewById(R.id.search);

        adapter = new SimpleCursorAdapter(this, R.layout.item_self,null,new String[]
                {"display_name","data1"}, new int[]{R.id.tv_name,R.id.tv_phone}, 
                SimpleCursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER);


        lv.setAdapter(adapter);

        //② 使用loader 加载数据  使用的 loader 的子类 CursorLoader
            //a) 让activity 或 Fragment 实现一个接口  LoaderCallbacks

        // ③得到loader 管理对象  initLoader 用于初始化 loader
        getLoaderManager().initLoader(7, null, this); // 第一个参数 就是为了 标识 这个 loader 的  第二个参数 传递的参数 没有 就写 Null


        search.setOnQueryTextListener(new OnQueryTextListener() {

            @Override
            public boolean onQueryTextSubmit(String query) {

                //输入完了 执行这个方法

                return false;
            }

            @Override
            public boolean onQueryTextChange(String newText) {

                //输入的过程中执行该方法
                //参数是用户输入的文本
                // 
                Bundle args = new Bundle();
                args.putString("key",newText);

                // 重新启动 Loader 
                getLoaderManager().restartLoader(7, args, MainActivity.this);

                return false;
            }
        });


    }


    @Override
    public Loader<Cursor> onCreateLoader(int id, Bundle args) {
        // 创建Loader  Loader 和 resolver  区别 只是 一个主线程 一个子线程 他们是类似的

        String where = null;
        String[] whereArgs = null;

        if(args!=null){

            String data = args.getString("key");
            where = "display_name like ? or data1 like ?";
            //意思是 只要含有就查出来
            whereArgs = new String[]{"%"+data+"%","%"+data+"%"};

        }

        return new CursorLoader(this, contactUri, columns, where, whereArgs, null);



    }



    @Override
    public void onLoadFinished(Loader<Cursor> loader, Cursor data) {

        //loader 加载完数据执行 该方法 由主线程执行
                adapter.swapCursor(data);

    }


    @Override
    public void onLoaderReset(Loader<Cursor> loader) {
        //重置 Loader的时候执行  相当于  
        adapter.swapCursor(null);// 重新查询了 数据有变化了  重新用 loader 查询数据

    }





}
Android开发技术周报:工具更新与性能优化实践 Android开发技术周报作为开发者获取最新技术动态的重要渠道,系统性地整合了工具链更新、框架优化和实践经验。从Android Studio的功能增强到Jetpack组件的最新特性,技术周报帮助开发者快速掌握核心更新。例如WorkManager 2.8.0的任务链执行效率提升40%,Compose动画系统新增AnimatedContent组件,这些优化直接提升了应用性能和开发效率。对于构建速度优化,Gradle 8.0的配置缓存和KSP替代kapt等方案能显著缩短构建时间。内存泄漏排查方面,Android 阅读详情

相关推荐

Android存储访问框架SAF:原理、API详解与工程实践

在Android应用开发中,文件系统访问是基础且关键的技术环节。传统基于文件路径的直接访问方式存在安全漏洞和权限滥用问题,其核心缺陷在于缺乏精细的访问控制。Android系统为此引入了基于URI的内容提供者模型,通过统一的资源标识机制实现安全可控的文件访问。Storage Access Framework(SAF)正是这一理念的工程实现,它采用基于用户意图的访问模型,通过系统级文件选择器让用户精确授权特定文件或目录。该框架的技术价值在于解决了跨应用文件共享的安全性与标准化问题,同时统一了本地存储与云端服务的

weixin_30820077的博客 478

Android基础——ContentProvider和contentResolver

ContentProviderContentProvider是什么?权限运行时权限 ContentProvider是什么? 利用ContentProvider可实现在不同应用程序之间的数据共享,并保证被访问数据的安全性。 权限 普通权限:不会直接威胁到用户安全和隐私的权限,这部分权限会自动授权,不再需要手动操作 危险权限:可能会触及用户隐私或对设备安全性造成影响的权限,必须要由用户手动授权,否则无法使用。危险权限需要进行运行时权限处理 运行时权限 ...

松仔Log的博客 1万+

Android Launcher启动原理:从systemReady到首帧渲染全链路解析

Launcher是Android系统中首个且最关键的Activity,其启动并非普通App流程,而是系统服务就绪后由ActivityManagerService(AMS)触发的基础设施级调度。它依赖PackageManagerService(PMS)完成组件解析、Intent匹配与资格校验,经Zygote进程孵化、Application创建、Activity生命周期激活等多层协作,最终抵达onResume与首帧渲染。该过程深度耦合AMS、PMS、WMS及Zygote四大核心模块,既是Android应用生命周

weixin_33796177的博客 372

android contentResolver的使用

今天,简单讲讲android 如何使用contentResolver。 这个contentResolver其实是属于ContentProvider 的内容,我之前一直没有用到android的ContentProvider ,所以昨天看到contentResolver时,居然不知道contentResolver怎么使用,后来,在网上查找了资料,最终解决了问题。这里记录一下。 在A

谢岩的博客 2万+

Android ContentResolver的使用

本文介绍了ContentResolver的使用方法,包括查询数据、插入数据、更新数据和删除数据。通过ContentResolver,我们可以方便地与ContentProvider进行数据交互,实现数据的读取和修改。它提供了一组方法,用于查询、插入、更新和删除ContentProvider中的数据。本文将详细介绍ContentResolver的使用方法,并提供相应的源代码示例。首先,需要构建一个Uri对象,指定要查询的数据的位置和条件。除了使用Uri查询数据外,还可以使用SQL语句来查询数据。

ByteWhizX的博客 1125

Cocos Creator Android头像上传全链路解决方案

在移动跨平台开发中,图像采集与上传是基础但高危的技术环节,涉及权限管理、Native桥接、Canvas像素处理、文件路径适配及服务端协同等多层原理。尤其在Android平台,自6.0起的运行时权限模型、11+的分区存储、13+的媒体权限收紧,使相机/相册调用极易失败。本方案以Cocos Creator为前端框架,系统性覆盖从Intent启动、content://URI解析、Canvas裁剪压缩,到multipart上传协议设计与本地缓存复用的完整技术闭环,兼顾工程鲁棒性与答辩可演示性,适用于高校课设、毕设及

weixin_28197941的博客 251

Android ContentResolver

*registerContentObserver(Uri uri, boolean notifyForDescendants, ContentObserver observer)**方法的第四个参数是flags,用于指定注册ContentObserver的标志。ContentResolver.registerContentObserver()方法除了常用的异步方法之外,还提供了一些同步方法,用于阻塞当前线程,直到观察到的Uri发生变化。这两个方法的第一个参数是Uri,用于指定要观察的Uri。

嗯... 5431

大华/华睿工业相机(摄像头)链接电脑,并用OpenCV打开

睿科是大华旗下机器视觉子公司,现在工业相机一般是华睿在产,要下载驱动程序,要到华睿官网哪里下载。由于我的电脑没有摄像头,所以摄像头序列化为0,电脑的第一个摄像头默认为0,序列号是0,1,2,3……,你是什么接口连接的就选择什么, 建议直接全选。我这里选择第二个,下载后点击安装,的你要点击识别右侧设置,设置。这个过程很简单,故不赘述。打开你的设备会在右边显示。

qq_48050838的博客 1万+

ContentProvider与ContentResolver

ContentProvider与ContentResolver及ContentObserve监听

蔡林浩的博客 2016

Windows10 使用Apple Studio Display显示器的设置

AppleStudioDisplay显示器购买花了近1.5wRMB,由于为windows台式机,显卡为NVIDAGTX-1660,而AppleStudioDisplay只有雷电接口,尝试了很多种转接方式,均以失败告终,最终使用贝尔金VR线成功,,附图如下这边也测试过NVIDARTX-2060Super、NVIDAGTX-1650显卡,都是能点亮的,NVIDA1650存在关机重启后黑屏,不稳定现象,2060也存在关机重启后不亮现象,后面发现1660s很稳定。...

爱意随风起,人生不可弃。 1万+

SAP采购含税价转换的底层逻辑解析:ABAP例程如何实现价税分离计算

本文深入解析SAP系统中采购含税价与不含税价的转换机制,重点介绍VOFM例程和ABAP代码实现价税分离计算的方法。通过详细讲解数学原理、税率体系及SAP定价引擎架构,为开发人员提供完整的解决方案,帮助提升采购业务中的价格处理效率和准确性。

weixin_29237635的博客 451

Android实现获取本机中所有图片(Loader,CursorLoader,LoaderManager,SimpleCursorAdapter的简单应用)

用 CursorLoader 查 MediaStore 时,投影漏掉 _ID 会让 SimpleCursorAdapter 直接抛异常。本文从 LoaderManager 初始化讲到 swapCursor 绑定与权限排障,给出可复制的 Android 相册图片列表实现,并附 TaoToken 官网 https://taotoken.net/?utm_source=taotoken_aicg_blog_end 辅助定位报错。

weixin_42577243的博客 8

中文实体关系抽取数据集大盘点:从百度Duie2.0到医疗CBLUE,哪个更适合你的NLP项目?

本文全面分析了中文实体关系抽取领域的主流数据集,包括百度DuIE 2.0、医疗CBLUE等,帮助开发者根据项目需求选择最适合的数据集。文章详细对比了各数据集的特点、适用场景及优化策略,为自然语言处理项目提供实用指南。

weixin_29284657的博客 122

3 步完成 HMCL 主题定制:内置主题色、背景图与自定义颜色值完整指南

默认的启动器界面用上一阵子,难免看腻:一样的蓝白色调、同一张内置壁纸、一成不变的字体。其实 HMCL(跨平台的 Minecraft 启动器)内置了相当完整的主题定制系统——主题色、背景图、字体,甚至标题栏和窗口透明度,都能在"设置"里的"个性化"页面直接调。这篇文章按"先挑色、再换背景、最后用颜色值微调"的顺序,带你走完 HMCL 主题定制,再补上几个不容易发现的细节。 ## 分步实操:三步调好

gitblog_00161的博客 314

Android各个版本存储权限适配

虽然 Android10 上面提出了外部存储分区的概念,不过之前的版本中,我们只要为应用添加了。1、AndroidManifest添加权限设置。3、拒绝权限时跳转详细设置页面。就可以像之前的方式一样访问手机的外部存储空间。2、请求所有文件管理权限。

sig321的专栏 1848

【SigmaStudio】自定义算法组件之源码规范(二)

工作中自定义算法组件一般是dll文件,生成dll文件需要XML文件和DLB文件,记录一下DLB文件代码的编码规范,定义SigmaStudio SHARC算法开发的编码规则,涵盖函数原型、内存管理、接口结构体等关键要求,确保算法模块与SigmaStudio环境兼容

liang_song的博客 1377

Android通讯录开发实战:从权限申请到拨号调用的完整解决方案

在Android应用开发中,ContentProvider作为系统数据访问的核心机制,为开发者提供了统一的数据操作接口。其原理是通过URI标识和权限控制,实现对系统数据(如联系人、媒体文件)的安全访问。这一机制的技术价值在于保障了系统数据的安全性和应用的沙盒隔离,同时为开发者提供了标准化的数据交互方式。在涉及用户隐私数据的场景下,如通讯录访问,开发者必须遵循运行时权限模型,动态申请READ_CONTACTS等危险权限。本文聚焦于通讯录数据查询与拨号功能实现,通过实战代码演示了如何结合ContentProvi

weixin_34246551的博客 2143

SIWAVE仿真PCB操作说明

使用SIWAVE进行PCB仿真提取S参数的操作

sinat_15150363的博客 3071

Android DB Commons 项目推荐

Android DB Commons 项目推荐 android-db-commons Some common utilities for ContentProvider/ContentResolver/Cursor and other db-related android stuff ...

gitblog_00035的博客 467

【推荐100个unity插件】unity易于使用模块化设计的天空、体积云和天气系统——Enviro 3

Enviro 3是一款功能强大的Unity天空与天气系统插件,提供动态天空、体积云、天气模拟等丰富功能。安装时需将预制体拖入场景并配置主相机,URP支持需激活深度纹理和添加渲染特性。模块化设计允许自由添加/移除时间、光照、雾效等模块,并通过API控制参数。推荐配合色调映射(如ACES模式)获得最佳视觉效果。插件支持季节、温湿度模拟及闪电风暴等特效,适用于需要逼真环境渲染的Unity项目。

向宇的博客,专注php/web全栈 unity游戏开发,欢迎大家评论纠错 2095

jdk-8u144-linux-x64.tar.gz.

该资源为搭建Linux系统Java环境用,资源的后缀为tar.gz格式的压缩包

亿连车机版V7.0.1:Android车载适配的合规分水岭

Android车载应用适配本质上是围绕系统版本、ABI架构、文件访问模型与权限体系展开的工程实践。随着Android 10+强制推行Scoped Storage沙箱机制和AAOS兼容要求,传统基于路径直读、32位so库、file://URI及Legacy Service的开发范式已失效。亿连车机版V7.0.1正是这一技术演进的关键节点——它通过targetSdkVersion≥29、arm64-v8a/x86_64双ABI限定、FileProvider URI重构及CarService生命周期强约束,倒逼车

weixin_34343308的博客 402

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

Android开发必备开源库解析与最佳实践

在Android应用开发中,开源库作为基础架构的重要组成部分,极大提升了开发效率和应用性能。从网络通信的Retrofit+OkHttp组合,到异步处理的Kotlin协程,再到图片加载的Glide,这些经过验证的解决方案都遵循单一职责原则,并提供了灵活的扩展接口。开源库的核心价值在于避免重复造轮子,使开发者能够专注于业务逻辑实现。在UI层,Jetpack Compose带来了声明式编程的新范式;在性能优化方面,LeakCanary等工具帮助开发者快速定位内存问题。合理选择和维护活跃的开源库,是构建高质量And

weixin_34194087的博客 488

迈瑞BS系列全自动生化分析仪LIS协议接口手册(内含HL7和ASTM)

迈瑞BS系列全自动生化分析仪LIS协议接口手册,内含HL7和ASTM)

汉书HE8,好用的汇编代码编写工具

汉书HE8,好用的汇编代码编写工具早期编写汇编代码所用功能强大

Android MediaLoader

# MediaLoader 媒体查询 android 读取本地相册 视频照片 之前读取的方式 是视频照片 分开读取 然后还要 按照时间倒序排序 如果照片视频很多的话就会加载缓慢 2800{视频+照片(照片多数)} 加载大概需要7-8秒的样子 不能忍受后来查资料的时候我发现一个不错的开源库 github.com/sucese/phoe… 知道了LoaderManger 之前加载 都是Async...

weixin_34242658的博客 576

Android 使用AsyncTaskLoader获取手机联系人:TaoToken 统一 Key 通道下的可复现配置

Android 用 AsyncTaskLoader 后台读取手机联系人,配合 TaoToken 统一 Key 通道完成鉴权配置。本文给出可复制的 Loader 骨架、READ_CONTACTS 权限声明与 Base URL、Key、Model ID 三件套参数,并在真机验证线程 ID 与请求返回一致,附 401、local proxy failed 等常见报错排查表。详见 https://taotoken.net/?utm_source=taotoken_aicg_blog_end

weixin_42588672的博客 8

Android 中的 adapter 和作用以及常见的 adapter:从 BaseAdapter 到 FragmentPagerAdapter 的配置骨架

Android 列表渲染卡在 Adapter 层?本文梳理 BaseAdapter、ArrayAdapter、FragmentPagerAdapter 的选型边界与骨架代码,并给出在 Cline 的 settings.json 中接入 TaoToken 统一 Key/API 通道的验证步骤,一次跑通列表渲染与分页切换。详见 https://taotoken.net/?utm_source=taotoken_aicg_blog_end

weixin_28949937的博客 171

Android registerContentObserver 原理与实战避坑

Android 数据变更通知体系中,ContentObserver 用于监听 MediaStore、联系人、Settings 等 ContentProvider。registerContentObserver 不传数据,只是把 Binder 观察者注册到 system_server 的 ContentService,由 ObserverNode 树按 uri 层级匹配;notifyForDescendants 与 notifyChange flags 共同决定通知是否命中,回调线程取决于构造时传入的 Han

weixin_34228387的博客 404
上一篇: Android自定义内容提供者使用
下一篇: Android适配器详解
一朵红杏
博客等级 码龄12年 51粉丝 282原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值