Objective-C Итерация по NSString для получения символов
У меня есть эта функция:
void myFunc(NSString* data) {
NSMutableArray *instrs = [[NSMutableArray alloc] initWithCapacity:[data length]];
for (int i=0; i < [data length]; i++) {
unichar c = [data characterAtIndex:i];
[instrs addObject:c];
}
NSEnumerator *e = [instrs objectEnumerator];
id inst;
while (inst = [e nextObject]) {
NSLog("%i\n", inst);
}
}
Я думаю, что это не удается в [instrs addObject:c]
, Его цель - перебирать шестнадцатеричные числа строки NSString. Что приводит к сбою этого кода?
2 ответа
unichar
не является объектом; это целочисленный тип.
NSMutableArray
может только держать предметы.
Если вы действительно хотите положить его в NSMutableArray
, вы можете обернуть целочисленное значение в NSNumber
объект: [instrs addObject:[NSNumber numberWithInt:c]];
Но какой смысл вначале вставлять значения в массив? Вы знаете, как перебирать строки и получать символы, зачем помещать их в массив, чтобы снова перебирать их?
Также обратите внимание, что:
- формат "%i" NSLog ожидает целое число; Вы не можете передать это объект
- для шестнадцатеричного вывода вы хотите "%x", а не "% i"
Если функция предназначена только для отображения символов в виде шестнадцатеричных значений, вы можете использовать:
void myFunc(NSString* data)
{
NSUInteger len = [data length];
unichar *buffer = calloc(len, sizeof(unichar));
if (!buffer) return;
[data getCharacters:buffer range:NSMakeRange(0, len)];
for (NSUInteger i = 0; i < len; i++)
NSLog(@"%04x", (unsigned) buffer[i]);
free(buffer);
}
Это немного более эффективно, чем ваш подход (кроме того, в вашем подходе вы никогда release
instrs
массив, поэтому он будет просачиваться в среде без сбора мусора).
Если строка содержит шестнадцатеричные числа, вы захотите многократно использовать NSScanner
"s scanHexInt:
метод, пока не вернется NO
,
void myFunc(NSString* data)
{
NSScanner *scanner = [[NSScanner alloc] initWithString:data];
unsigned number;
while ([scanner scanHexInt:&number])
NSLog(@"%u", number);
[scanner release];
}