将自定义对象的 NSArray 转换为带有索引的按字母顺序划分的 UITableView?

发布于 2024-09-29 16:10:56 字数 791 浏览 0 评论 0原文

(嗯..长标题)

如果我从一个自定义对象的 NSArray(每个对象都是一个人)开始,如下所示:

{
  surname:Allen   forename: Woody,
  surname:Baxter  forename: Stanley,
  surname:Clay    forename: Cassius
}

..等等..

您可以看到该数组已经按姓氏顺序排列。我如何使用该数组创建一个 UITableView ,其中包含节标题 A、BC 等,以及侧面垂直运行的索引

                                                               A
                                                               B
                                                               C

编辑

我想我要问的是如何将我的将对象数组放入一个节数组中,其中包含姓氏的所有第一个字母,以及一个姓氏数组,它可能是一个像这样的嵌套数组:

{ 
  letter: a
  {  surname:Allen   forename: Woody   }
  letter: b
  {  surname:Baxter  forename: Stanley }
  etc
} 

事实上,也许只是一个嵌套数组就可以了。

(hmm.. long title)

If I start out with an NSArray of custom objects (each object is a Person) like this:

{
  surname:Allen   forename: Woody,
  surname:Baxter  forename: Stanley,
  surname:Clay    forename: Cassius
}

..etc..

You can see that the array is already in surname order. How do I use that array to create a a UITableView with a section headers A, B C etc, as well as an index thing on the side running vertically

                                                               A
                                                               B
                                                               C

EDIT

I guess what I'm asking is how to turn my array of objects into a Section Array, with all the first letters of the Surnames, and a Surname Array which is perhaps a nested array like this:

{ 
  letter: a
  {  surname:Allen   forename: Woody   }
  letter: b
  {  surname:Baxter  forename: Stanley }
  etc
} 

In fact, perhaps just a nested array will do.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

樱娆 2024-10-06 16:10:56

可能有一百万种方法可以做到这一点:)这是一种可能有效的方法(我确信它可以做得更漂亮,但因为没有人回答):

NSMutableDictionary *aIndexDictionary = [[NSMutableDictionary alloc] init]; 
NSMutableArray *currentArray;
NSRange aRange = NSMakeRange(0, 1);
NSString *firstLetter;
for (Person *aPerson in personArray) {
  firstLetter = [aPerson.surname substringWithRange:aRange];
  if ([aIndexDictionary objectForKey:firstLetter] == nil) {
    currentArray = [NSMutableArray array];
    [aIndexDictionary setObject:currentArray forKey:firstLetter];
  }
  [currentArray addObject:aPerson];
}

未经测试......

There are probably a million ways of doing this :) Here's one that might work (I am sure it can be done much prettier, but since no one is answering):

NSMutableDictionary *aIndexDictionary = [[NSMutableDictionary alloc] init]; 
NSMutableArray *currentArray;
NSRange aRange = NSMakeRange(0, 1);
NSString *firstLetter;
for (Person *aPerson in personArray) {
  firstLetter = [aPerson.surname substringWithRange:aRange];
  if ([aIndexDictionary objectForKey:firstLetter] == nil) {
    currentArray = [NSMutableArray array];
    [aIndexDictionary setObject:currentArray forKey:firstLetter];
  }
  [currentArray addObject:aPerson];
}

Untested...

冷︶言冷语的世界 2024-10-06 16:10:56

约瑟夫·图拉的答案有很多问题,正如他提到的,它未经测试。问题如下:

1) 如果 name 为 nil 或 @"",[aPerson.name substringWithRange:aRange] 将崩溃;

2)如果firstLetter已经在键列表中,则当前数组不会重置为指向属于键firstLetter的数组对象。因此,如果 currentArray 先前指向字典中键为“K”的数组,但当前的第一个字母“P”已作为键存在,则将添加名称(以该字母“P”开头)以“k”开头的名称数组。那里有大问题。

3) 由于大小写的不同,Jassie 被添加到与 jassie 不同的数组中(大写和小写“k”的处理方式不同)。

因此,作为对 Joseph 答案的巨大改进,第 2 点至关重要,这里为未来的用户提供了更准确的实现:

-(NSDictionary*)indexArrayByName:(NSArray*)people
{
    NSMutableDictionary *anIndexedDict = [[NSMutableDictionary alloc] init];
    NSMutableArray *currentArray = nil;
    NSRange aRange = NSMakeRange(0, 1);
    NSString *firstLetter;

    for(Person *aPerson in people)
    {
        if(aPerson.name.length)
            firstLetter = [[aPerson.name substringWithRange:aRange] uppercaseString];
        else
            firstLetter = @"noName";//find own way to identify these

        if(![anIndexedDict.allKeys containsObject:firstLetter])
        {
            currentArray = [NSMutableArray array];
            anIndexedDict[firstLetter] = currentArray;
        }
        currentArray = anIndexedDict[firstLetter];
        [currentArray addObject:aPerson];
    }    
    return anIndexedDict;
}

可以添加其他改进,例如删除前导空格等,但我只是想我会提到主要问题。我测试了约瑟夫对这些问​​题的答案,然后测试了我的答案以确保它们被消除:)。主要思想归功于约瑟夫。干杯。

Joseph Tura's answer has a number of issues, its untested as he mentioned. Here are the issues:

1) [aPerson.name substringWithRange:aRange] will crash if the name is nil or @"";

2) If firstLetter is already in the list of keys, current array is not reset to point to the array object that belongs to the key firstLetter. So if the currentArray previously pointed to an array whose key in the dictionary is 'K', and yet the current firstLetter being 'P' already existing as a key, the name (that starts with the that letter 'P') will be added to the array of names starting with 'k'. Big issue there.

3) Jassie is added to different array to jassie as a result of difference in the case (uppercase and lowercase 'k' are treated differently).

So, as a huge improvement to Joseph's answer, point number 2 being critical, here is a more accurate implementation for future users:

-(NSDictionary*)indexArrayByName:(NSArray*)people
{
    NSMutableDictionary *anIndexedDict = [[NSMutableDictionary alloc] init];
    NSMutableArray *currentArray = nil;
    NSRange aRange = NSMakeRange(0, 1);
    NSString *firstLetter;

    for(Person *aPerson in people)
    {
        if(aPerson.name.length)
            firstLetter = [[aPerson.name substringWithRange:aRange] uppercaseString];
        else
            firstLetter = @"noName";//find own way to identify these

        if(![anIndexedDict.allKeys containsObject:firstLetter])
        {
            currentArray = [NSMutableArray array];
            anIndexedDict[firstLetter] = currentArray;
        }
        currentArray = anIndexedDict[firstLetter];
        [currentArray addObject:aPerson];
    }    
    return anIndexedDict;
}

Other improvements can be added e.g removing leading white spaces etc, but I just thought I'ld mention the main issues. I tested Joseph's answer for those issues, and then mine to make sure they are eliminated :) .Credit to Joseph for main idea. Cheers.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文