无法选择所有符合IN子句的电话号码的联系人

时间:2012-06-20 22:45:05

标签: android android-contacts android-contentprovider android-sqlite

我正在尝试弄清楚如何使用电话号码列表查询Android联系内容提供商,以检索具有与该列表中的项目匹配的电话号码的联系人。在直接的SQL中,我会使用类似的东西:

  

SELECT * FROM PHONES WHERE NUMBER IN ('1234','1235')

我不能,因为我正在使用CP API,我似乎错过了一些东西。这是onCreateLoader()查询的片段。此查询的结果中没有返回任何记录,但我知道数据库中的联系人存在这些电话号码。我认为没有找到任何记录,因为它存储在数据库中的电话号码的格式如下:

  

+1 425-555-1212

我不知道是否有办法查询CP并让它根据无格式数据评估我的IN()查询列表。以下是onCreateLoader()查询:

public Loader<Cursor> onCreateLoader(int id, Bundle args) {
    String[] projection = new String[] {    
            ContactsContract.CommonDataKinds.Phone._ID,
            ContactsContract.CommonDataKinds.Phone.CONTACT_ID,
            ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME,
            ContactsContract.CommonDataKinds.Phone.LABEL,
            ContactsContract.CommonDataKinds.Phone.LOOKUP_KEY,
            ContactsContract.CommonDataKinds.Phone.NUMBER};
    return new CursorLoader(
            getActivity().getApplicationContext(), 
            ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
            projection,
            ContactsContract.CommonDataKinds.Phone.NUMBER+" IN ('4255551212','4255551213')",
            null,
            null);
}

使用PhoneLookup(如下所示)与上一个查询中的一个电话号码实际产生正确的联系人匹配,因此我假设必须有这样做的方法。很遗憾,PhoneLookup似乎无法处理电话号码列表,但只能处理一个电话号码:

public Loader<Cursor> onCreateLoader(int id, Bundle args) {
    String[] projection = new String[] {
            ContactsContract.PhoneLookup._ID,
            ContactsContract.PhoneLookup.DISPLAY_NAME,
            ContactsContract.PhoneLookup.LABEL,
            ContactsContract.PhoneLookup.LOOKUP_KEY,
            ContactsContract.PhoneLookup.NUMBER};
    return new CursorLoader(
            getActivity().getApplicationContext(),
            Uri.withAppendedPath(ContactsContract.PhoneLookup.CONTENT_FILTER_URI, Uri.encode("4255551212")),
            projection,
            null,
            null,
            null);
}

有没有办法实现这一目标,还是有另一种方法可以产生相同的结果?结果是:

  • 根据电话号码列表,选择列表中包含电话号码的所有联系人

有什么建议吗?

1 个答案:

答案 0 :(得分:3)

首先,我认为没有办法在ContactsContract.PhoneLookup附加多个电话号码。

其次,正如您所说,ContactsContract.CommonDataKinds.Phone中存储的数字通常是格式化的。确定两个电话号码是否相等的方式基于PhoneNumberUtils.compare(String num1, String num2)。 通过阅读源代码here,您可能会想出如何生成数字变体列表并将其全部包含在IN ('num1', 'num2', ...)

如果您需要查找大量数字(即与整个联系人大小几乎相同),建议您从ContactsContract.CommonDataKinds.Phone查询所有NUMBER和所需数据,并将其存储在HashMap<NumberString, TheDataYouWant>中。 (在此之前,您需要创建一个NumberString类,其中包含一个字符串并覆盖compareTo()方法以返回PhoneNumberUtils.compare(this.string, anotherNumber.string);)。然后您可以在{{1}中搜索所需的数字}}