2

こんにちは、現在連絡先に関連するプロジェクトを行っています。連絡先から詳細を取得しています* (Eメール、番号、連絡先名) *うまくいきますが、問題は連絡先の詳細を取得するのに長い時間がかかることです(1000以上の連絡先ソーシャルネットワークサイトから同期する連絡先を含む) 。この目的のために置くのでAsynchronous Task、うまくいきますが、問題はフェッチプロセスを完了するのに長い時間がかかるためです。戻るボタンを押すと、非同期タスク中にクラッシュします。 。このフェッチ連絡先に時間がかかる理由は問題ではありませんcontact。高速化する方法はありますか。連絡先の詳細を取得するための私のコードは次のとおりです

public void readContact() {
    contactname = new ArrayList<String>();
    contactnumber = new ArrayList<String>();
    companyname_one = new ArrayList<String>();
    contactemail = new ArrayList<String>();
    people = getContentResolver().query(
            ContactsContract.Contacts.CONTENT_URI, null, null, null,
            PhoneLookup.DISPLAY_NAME);

    while (people.moveToNext()) {
        int nameFieldColumnIndex = people
                .getColumnIndex(PhoneLookup.DISPLAY_NAME);
        String contact = people.getString(nameFieldColumnIndex);
        if (contact == null) {
            contactname.add("No contact Set");
        } else {

            contactname.add(contact);

        }

        String szId = people.getString(people
                .getColumnIndexOrThrow(ContactsContract.Contacts._ID));

        cursor_one = getContentResolver().query(
                ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
                null,
                ContactsContract.CommonDataKinds.Phone.CONTACT_ID + "='"
                        + szId + "'", null, null);
        if (cursor_one.moveToNext()) {
            String number = cursor_one.getString(cursor_one
                    .getColumnIndex(Phone.NUMBER));
            contactnumber.add(number);
            cursor_one.close();

        } else {
            contactnumber.add("no number");
            cursor_one.close();

        }

        emails_value = getContentResolver().query(
                Email.CONTENT_URI,
                null,
                ContactsContract.CommonDataKinds.Phone.CONTACT_ID + "='"
                        + szId + "'", null, null);

        if (emails_value.moveToNext()) {
            email_sorting = emails_value.getString(emails_value
                    .getColumnIndex(Email.DATA));
            checkAll();

        } else {

            contactemail.add("no email");
            emails_value.close();

        }

    }

    people.close();


    System.out.println("noz " + contactnumber);
    System.out.println("name" + contactname);
    System.out.println("email" + contactemail);
    System.out.println("noz size " + contactnumber.size());
    System.out.println("name size " + contactname.size());
    System.out.println("contactemail size " + contactemail.size());



}

方法は以下のようにメールのcheckAll()パターンマッチングです

    public boolean checkAll() {

    boolean chkAll = true;
    Pattern p1 = Pattern.compile(".+@.+\\.[a-z]+");
    Matcher m1 = p1.matcher(email_sorting.trim());

    if (!m1.matches()) {

        contactemail.add("no email");
        contactemail_sort.add("no email");
        emails_value.close();
        chkAll = false;


    } else {

        contactemail.add(email_sorting);
        contactemail_sort.add(email_sorting);
        emails_value.close();
        chkAll = true;
    }

    return chkAll;
}
4

2 に答える 2

3

わかりました、私はこれが機能するための最良の方法をようやく見たと思います。アダプタを作成する前にすべての連絡先情報を引き出す代わりに、カーソルを受け入れ、バックグラウンドスレッドで実行されるクエリをpeopleカスタムビューに入力するカスタムCursorAdapterを作成する必要があります。cursor_oneこれは、ListViewの自然な遅延読み込みを利用して、これを希望どおりに機能させる必要があります。

少なくともAndroid3.0を使用している場合は、AsyncTaskを使用する代わりにローダーを使用できます。

ここで、例を作成するために使用したカスタムカーソルアダプターの例を見つけました。これをコードに実装するためのより良い方法はおそらくありますが、これは少なくとも、オーバーライドするメソッドとそれらに何を入れるかを示しています。

public class ContactListCursorAdapter extends SimpleCursorAdapter {

    private Context context;

    private int layout;

    public ContactListCursorAdapter (Context context, int layout, Cursor c, String[] from, int[] to) {
        super(context, layout, c, from, to);
        this.context = context;
        this.layout = layout;
    }

    // Used to populate new list items
    @Override
    public View newView(Context context, Cursor cursor, ViewGroup parent) {

        Cursor c = getCursor();

        final LayoutInflater inflater = LayoutInflater.from(context);
        View v = inflater.inflate(layout, parent, false);

        int nameCol = c.getColumnIndex(People.NAME);

        String name = c.getString(nameCol);

        /**
         * Next set the name of the entry.
         */     
        TextView name_text = (TextView) v.findViewById(R.id.name_entry);
        if (name_text != null) {
            name_text.setText(name);
        }

        getDeatils(v,c);

        return v;
    }

    // Used to bind a new item from the adapter to an existing view
    @Override
    public void bindView(View v, Context context, Cursor c) {

        int nameCol = c.getColumnIndex(People.NAME);

        String name = c.getString(nameCol);

        /**
         * Next set the name of the entry.
         */     
        TextView name_text = (TextView) v.findViewById(R.id.name_entry);
        if (name_text != null) {
            name_text.setText(name);
        }

        getDetails(v,c);
    }

    private void populateDetails(View v, Cursor c) {
       // Start your AsyncTask or Loader to get the details.
       // Be sure to populate the view with the results in the
       // appropriate completion callback.
    }
}
于 2012-08-16T17:45:28.350 に答える
0

私の提案は、構造がどのように機能するかを再定義することです。たとえば、連絡先、表示名、その他のメタデータなどの基本情報をすばやく取得できます。それをリストなどに表示し、連絡先を選択または表示したときに、残りの情報を読み込みます。

これにより、速度が大幅に向上します。ただし、連絡先に関するすべてを一度にロードする必要がある場合は、実行する必要のあるクエリの数が原因で非常に遅くなります。

もう1つの提案は、それらを完了したものとしてユーザーに表示することです。そうすれば、ある程度の進歩があり、彼らはそれを見ることができます。「LoadingWait」というダイアログを表示するだけではありません。

于 2012-08-16T17:00:56.447 に答える