iOS / Objective-C:尝试扫描字符串以查找将分配给多个NSStrings的子字符串

时间:2011-07-08 06:03:33

标签: objective-c ios nsstring nsscanner substring

我正在尝试完成斯坦福iPhone编程(FA10)分配“Flickr Fetcher” - 到目前为止事情进展顺利,但我陷入了僵局:

我已经成功提取了“前100名”图片的位置,这些图片以字符串格式化为“国家,州,城市”。我想创建两个NSStrings - 一个是国家,另一个是国家和城市。从那里我可以做到

cell.textLabel.text = countryString;
cell.detailTextLabel.text = stateCityString;

在我的表中查看数据源方法。

From research on stackoverflow和Apple Documentaion,NSScanner似乎是我最好的选择 - 这就是我到目前为止所拥有的......

- (void)viewDidLoad {
    //Get the top 100 photos from Flickr
    self.topPlacesArray = [FlickrFetcher topPlaces];

    NSString *mainLabelString = [[NSString alloc] init];
    NSString *stringFromArray = [[NSString alloc] init];

    //This retrieves the string of the location of each photo
    stringFromArray = [topPlacesArray valueForKey:@"_content"];

    NSScanner *theScanner = [NSScanner scannerWithString:stringFromArray];
    NSCharacterSet *commaSet = [[NSCharacterSet alloc] init];
    commaSet = [NSCharacterSet characterSetWithCharactersInString:@","];

    while ([theScanner isAtEnd] == NO) {
        if ([theScanner scanUpToCharactersFromSet:commaSet intoString:&stringFromArray]) {
            NSLog(@"%@",stringFromArray);
        }
    }

我只是想看看字符串是否正确地自我子串 - 但是我在while循环的开始时得到一个“SIGBART”,错误是这样的:

*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[__NSArrayI length]: unrecognized selector sent to instance 0x8939eb0'

从我在NSScanner上看到的所有文档中,似乎我已经正确设置了它,但是,无论我做了什么改变,它似乎都无法开始循环。

如何正确设置NSScanner,以避免“SIGABRT”? (为了记录,我假设“SIGABRT”是一个段错误?)。谢谢大家的时间,大家都是最棒的!

(顺便说一句:我知道这个国家和州都尚未完全实施,我只想习惯NSScanner,一旦我控制了NSScanner,我将实施其余的工作)

编辑1:SosBorn!你太不可思议了!非常感谢!所以我已经为我的viewDidLoad实现了这个:

- (void)viewDidLoad
{
    self.topPlacesArray = [FlickrFetcher topPlaces];
    NSArray *ArrayOfStrings = [[NSArray alloc] init];
    NSArray  *placeElements = [[NSArray alloc] init];
    NSString *country = [[NSString alloc] init];
    NSString *city = [[NSString alloc] init];
    NSString *state = [[NSString alloc] init];

    ArrayOfStrings = [topPlacesArray valueForKey:@"_content"];

    for (NSString *place in ArrayOfStrings) {

        placeElements = [place componentsSeparatedByString:@", "];
        if ([placeElements count] == 3 && [placeElements objectAtIndex:0] != nil) {
           city = [placeElements objectAtIndex:0];
           [self.cityArray addObject:city];
           state = [placeElements objectAtIndex:1];
           [self.stateArray addObject:state];
           country = [placeElements objectAtIndex:2];
           [self.countryArray addObject:country];
           NSLog(@"%@, %@, %@", city, state, country);    
        }
       else {
           NSLog(@"Did this work?");
       }
    }

    [ArrayOfStrings release];
    [placeElements release];
    [country release];
    [city release];
    [state release];
    [super viewDidLoad];
}

这就像一个完整的魅力,但是当我试图访问self.window.rootViewController = self.viewController时,我在代表中遇到了一些不良访问 - 这没有任何意义(我实际上有一个完全空的表,等...) - 所以我认为我使用子字符串管理器进行了糟糕的内存管理,现在它在这个委托调用中遇到了麻烦。

Chuck,我对你的评论很感兴趣,因为我被告知制作变量的正确方法是调用[myclass alloc] init];当你完成后释放 - 就像我一样。当然,我的目标 - C绿色显示有点...... 脸红

你们所有人和这个令人难以置信的社区对我们学生来说是一笔财富 - 感谢你们所有的时间和奉献精神。进步的唯一途径是合作之路!

编辑2:好的 - 现在它已完全修复,没有可怕的泄漏问题。查克你是对的!我把alloc init的pricniples完全混淆了 - 这是我的最终解决方案:

    NSMutableArray *array1 = [[NSMutableArray alloc] init];
NSMutableArray *array2 = [[NSMutableArray alloc] init];
NSMutableArray *array3 = [[NSMutableArray alloc] init];

self.cityArray = array1;
self.countryArray = array2;
self.stateArray = array3;

[array1 release];
[array2 release];
[array3 release];


NSArray *ArrayOfStrings = [topPlacesArray valueForKey:@"_content"];
NSArray *topPlaces = [NSArray arrayWithArray:ArrayOfStrings];
NSArray *topPlacesSorted = [topPlaces sortedArrayUsingSelector:@selector(compare:)];
ArrayOfStrings = topPlacesSorted;

for (NSString *place in ArrayOfStrings) {
    NSArray *placeElements = [place componentsSeparatedByString:@", "];
    if ([placeElements count] == 3 && [placeElements objectAtIndex:0] != nil) {

        NSString *city = [placeElements objectAtIndex:0];

        [self.cityArray addObject:city];

        NSString *state = [placeElements objectAtIndex:1];

        [self.stateArray addObject:state];

        NSString *country = [placeElements objectAtIndex:2];

        NSString *stateAndCountry = [NSString stringWithFormat:@"%@, %@", state, country];

        [self.countryArray addObject:stateAndCountry];

        NSLog(@"%@, %@, %@", city, state, country);    
    }
   else {
       NSLog(@"Nil Request");
   }

再次感谢SosBorn,我觉得我已经忘记了CSಠಠ的基本知识。 唯一真正困扰我的是为什么我们必须以这种方式初始化实例NSMutableArrays - 我发现这是唯一的方式让它们实际工作。

1 个答案:

答案 0 :(得分:1)

不完全确定崩溃的原因,但我认为另一种方法可以更好地为您服务。你有一个topPlacesArray,为什么不迭代数组并单独处理每个数组项呢?我正在对topPlacesArray做一些假设,但它看起来像这样:

for (NSString *place in topPlacesArray)
{
  //Place is probably in this format: "Country, State, City"
  NSArray *placeElements = [place componentsSeperatedByString:@","];
  //This should give you an array with three elements. Country State and city.
  NSString *country = [placeElements objectAtIndex:0];
  NSString *cityState = [NSString stringWithFormat:@"%@, %@", country, cityState];
  //Now you have your strings that you need. Do whatever you need to do with them.
  //Add them to an array or set the value of a text label, etc.
}

没有花时间处理内存管理,但你明白了。