ABAddressBookCopyArrayOfAllPeople和ABAddressBookGetPersonCount返回不同的大小

gui*_*man 6 iphone iphone-sdk-3.0 abaddressbook ios4 ios

我有一个应用程序偶尔会崩溃,因为ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering()返回的数组与ABAddressBookGetPersonCount()的大小不同.代码的shell如下所示.通常nPeople与数组大小相同.然而,在一个用户的iPhone上(或者至少,如一个用户所报告的那样),nPeople几乎是其两倍.我可以通过使用数组大小​​而不是ABAddressBookGetPersonCount()来停止崩溃.但是,我不确定这是否意味着我没有访问iPhone中的所有联系人.

  • 有没有人遇到过这个问题?
  • 为什么数字会有所不同?

我想知道这是否与存储在群组中的联系人有关(我不知道有群组 - 只是一个想法).此外,从用户的电子邮件地址,我怀疑他们使用MobileMe.我想知道是否与MobileMe同步会创建具有不同recordId的重复项,但不会删除现有的Contact,至少不会像ABAddressBookGetPersonCount()那样.

编辑:我已经对此进行了一些调查,并对问题的原因有一个相当好的想法.由于我想要一个排序的联系人数组,我使用了ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering().这需要一个地址簿源 - 我使用了默认源.我相信可以有各种来源 - 本地来源以及Exchange和MobileMe等其他来源.因此,我的数组最终将只有本地联系人,而ABAddressBookGetPersonCount()返回的数字将包括所有来源 - 因此我的崩溃.因此,我认为最好只使用我的应用程序中的本地数据,并使用ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering而不是ABAddressBookGetPersonCount返回的数组大小.

CFArrayRef allPeople = InSourceWithSortOrdering(addressBook, source, kABPersonSortByLastName);  

    CFIndex nPeople = ABAddressBookGetPersonCount(addressBook);

    for (int i = 0; i < nPeople; i++) 
    {
        ABRecordRef ref = CFArrayGetValueAtIndex(allPeople, i);
    }   
Run Code Online (Sandbox Code Playgroud)

Som*_*luk 13

ABAddressBookGetPersonCountABAddressBookCopyArrayOfAllPeople给出不同的数组.

ABAddressBookGetPersonCount - 返回通讯录中的人员记录数.ABAddressBookCopyArrayOfAllPeople - 返回通讯录中的所有人员记录.

所以有时候同一个人可能会有额外的记录.这就是为什么你可能会有不同的尺寸.


Jok*_*sui 9

我今天遇到了这个问题.我的应用程序也崩溃了一些特殊的iDevices.

码:

    ABRecordRef source = ABAddressBookCopyDefaultSource(addressBook);
    CFArrayRef allPeople = ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering(addressBook, source, kABPersonSortByLastName);

    CFIndex nPeople = ABAddressBookGetPersonCount(addressBook);

    for (int i = 0; i < nPeople; i++) {
        ABRecordRef person = CFArrayGetValueAtIndex(allPeople, i);
        // more thing with `person`
    }
Run Code Online (Sandbox Code Playgroud)

但它有时会崩溃.添加一些断点我发现它allPeople的数量小于nPeople.

通过谷歌搜索,我发现了这篇文章.我发现可能有问题ABAddressBookCopyDefaultSource.在这里,我得到了默认的来源,我必须得到所有的来源.

码:

CFArrayRef sources = ABAddressBookCopyArrayOfAllSources(addressBook);

CFIndex sourceCount = CFArrayGetCount(sources);

for (CFIndex i = 0; i < sourceCount; i++) {
    ABRecordRef currentSource = CFArrayGetValueAtIndex(source, i);
    int sourceType = [(__bridge NSNumber *)ABRecordCopyValue(currentSource, kABSourceTypeProperty) intValue];
    switch (sourceType) {

        case kABSourceTypeCardDAV:
            NSLog(@"kABSourceTypeCardDAV");
            break;

        case kABSourceTypeCardDAVSearch:
            NSLog(@"kABSourceTypeCardDAVSearch");
            break;

        case kABSourceTypeExchange:
            NSLog(@"kABSourceTypeExchange");
            break;

        case kABSourceTypeExchangeGAL:
            NSLog(@"kABSourceTypeExchangeGAL");
            break;

        case kABSourceTypeLDAP:
            NSLog(@"kABSourceTypeLDAP");
            break;

        case kABSourceTypeLocal:
            NSLog(@"kABSourceTypeLocal");
            break;

        case kABSourceTypeMobileMe:
            NSLog(@"kABSourceTypeMobileMe");
            break;

        default:
            break;
    }
    CFArrayRef allPeopleInSource = ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering(addressBook, currentSource, kABPersonSortByLastName);
    NSLog(@"Count of allPeopleInSource: %i", CFArrayGetCount(allPeopleInSource));
}
Run Code Online (Sandbox Code Playgroud)

然后我得到了

    kABSourceTypeCardDAV
    Count of allPeopleInSource: 7
Run Code Online (Sandbox Code Playgroud)

这意味着该来源中只有一个来源,只有7个记录.

但在我的地址簿中,我有79个联系人!

然后我犯了一个错误.我通过sourcesABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering,就像这样:

    CFArrayRef allPeople = ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering(addressBook, sources, kABPersonSortByLastName);
Run Code Online (Sandbox Code Playgroud)

有多少成员allPeople

72!

确切地说是不在的记录数sources.

我将CFArrayRef传递给ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering第二个参数,它需要一个ABRecordRef.如果我通过nil怎么办?

最后,我得到了代码:

    CFArrayRef allPeople = ABAddressBookCopyArrayOfAllPeopleInSourceWithSortOrdering(addressBook, nil, kABPersonSortByLastName);

    CFIndex nPeople = ABAddressBookGetPersonCount(addressBook);

    for (int i = 0; i < nPeople; i++) {
        ABRecordRef person = CFArrayGetValueAtIndex(allPeople, i);
        // more thing with `person`
    }
Run Code Online (Sandbox Code Playgroud)

现在我可以在通讯录中找到所有联系人.

它适用于我的所有iDevices!

我对我可怜的英语感到非常抱歉......

希望这个答案可以帮到你.

注意:现在我不完全理解sourceAddressBook中的内容,有人可以帮助我吗?