Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/225.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Android:手机联系人查询需要很长时间才能返回结果_Java_Android_Sql - Fatal编程技术网

Java Android:手机联系人查询需要很长时间才能返回结果

Java Android:手机联系人查询需要很长时间才能返回结果,java,android,sql,Java,Android,Sql,我正在开发Voip应用程序,所以我必须显示所有联系人,以便用户拨打该应用程序 因此,我使用了以下函数: public void GetContactsIntoArrayList(){ int i = 0 ; cursor = getActivity().getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,null, null, ContactsContract.C

我正在开发Voip应用程序,所以我必须显示所有联系人,以便用户拨打该应用程序

因此,我使用了以下函数:

public void GetContactsIntoArrayList(){
    int i = 0 ;
    cursor = getActivity().getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,null, null,  ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME);
    HashSet<String> tempHash = new HashSet<String >();
    while (cursor.moveToNext()) {
        Person per = new Person();
        Bitmap bit_thumb ;
        name = cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
        phonenumber = cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
        contactId = cursor.getColumnIndex(ContactsContract.Contacts._ID);
        per.setName(name);
        per.setNumber(phonenumber);
        //

        if(tempHash.add(name) ){
            i++ ;
            StoreContacts.add(per );
        }
    }
    Toast.makeText( getActivity()," "+i , Toast.LENGTH_LONG).show();
    cursor.close();
    adapter = new ContactListViewAdapter(getContext() , StoreContacts) ;
    contactsListView.setAdapter(adapter);
}
public void getcontactsintoraylist(){
int i=0;
cursor=getActivity().getContentResolver().query(ContactsContract.CommonDataTypes.Phone.CONTENT\u URI,null,null,null,ContactsContract.CommonDataTypes.Phone.DISPLAY\u名称);
HashSet tempHash=新HashSet();
while(cursor.moveToNext()){
每个人=新的人();
位图位_拇指;
name=cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataTypes.Phone.DISPLAY_name));
phonenumber=cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataTypes.Phone.NUMBER));
contactId=cursor.getColumnIndex(ContactsContract.Contacts.\u ID);
per.setName(名称);
per.setNumber(电话号码);
//
if(tempHash.add(name)){
i++;
StoreContacts.add(per);
}
}
Toast.makeText(getActivity(),“”+i,Toast.LENGTH_LONG.show();
cursor.close();
适配器=新的ContactListViewAdapter(getContext(),StoreContacts);
contactsListView.setAdapter(适配器);
}
当我的联系人数少于5000时,一切都很好

但现在我的手机上有20000个联系人,检索结果需要大约13秒的时间


有人能帮我提高吗

假设您的手机中有100000个联系人,光标需要一分钟才能加载,那么长的加载时间会让用户感到恼火。 一种解决方案是使用限制获取联系人,如

从表限制0,30中选择*

然后填充listview(RecyclerView)。 这种方式比抓取更有意义

从表中选择*

因为我们不能同时显示100000个联系人, 当用户开始滚动并到达第一个元素限制的底部时,获取下一个联系人限制并更新listview

因为在本例中,我们不处理SQL表, 在ContentProvider中设置限制

Cursor c = resolver.query(
    MyTable.CONTENT_URI,
    MyTable.PROJECTION,
    null,
    null,
    " limit 1 offset 2");

我通过分离游标变量初始化解决了我的问题

看起来是这样的:

cursor = getActivity().getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,null, null,  ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME);
我将其替换为以下代码:

    String[] projection = new String[]{ContactsContract.CommonDataKinds.Phone._ID, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME, ContactsContract.CommonDataKinds.Phone.NUMBER};
    String orderBy = ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME;
    Uri uri = ContactsContract.CommonDataKinds.Phone.CONTENT_URI;

    cursor =  getActivity().getContentResolver().query( uri, projection, null, null, orderBy) ;

现在它的工作20000联系需要1秒

谁能帮我改进一下。。。删除15K联系人。。。但说真的。。。从UI线程移动您可以移动的内容。。。这对时间没有帮助(因为没有比硬件更好的东西对这个迭代没有帮助),但至少你不会得到一个。。。您也可以尝试使用CursorAdapter-它将消除在开始时迭代所有元素的需要。请问是否有其他方法解决此问题?我的客户不会理解此问题。您唯一可以做的是将代码从主线程移动到某个工作线程,这样您就可以避免ANR。为什么客户必须理解这一点?他只会看到一个加载条,例如,启动时是否有可能预加载数据?不要使用
ContactListViewAdapter
-使用
SimpleCursorAdapter
,而不是使用
SimpleCursorAdapter
,非常感谢您提供此功能,但我认为我现在所做的就足够了–@pskink