要点:使用ARC; 完整错误是:
malloc: * mmap(size = 2097152)失败(错误代码= 12) 错误:无法分配区域 * *在malloc_error_break中设置断点以进行调试
四次。
问题的唯一代码是:
-(void)iterate:(NSString *)string{
frontString = NULL;
backString = NULL;
arrayOfNumbers = NULL;
backwardArrayOfNumbers = NULL;
nextString = NULL;
nextArrayOfNumbers = NULL;
nextArrayOfNumbers = [NSMutableArray new];
nextString = [NSMutableString new];
backwardArrayOfNumbers = [NSMutableArray new];
arrayOfNumbers = [NSMutableArray new];
frontString = [[NSMutableString alloc] initWithString:string];
backString = [NSMutableString new];
if (string.length > 1) {
iteration++;
for (unsigned long i = 0; i < string.length; ++i) {
NSString *sub = [string substringWithRange:(NSRange){i, 1}];
[arrayOfNumbers addObject:sub];
NSString *back = [string substringWithRange:(NSRange){string.length-(i+1), 1}];
[backwardArrayOfNumbers addObject:back];
[backString appendString:back];
sub = NULL;
back = NULL;
}
if ([frontString isEqualToString:backString]) {
[palindromicNumberTextView setText:string];
[iterationLabel setText:[NSString stringWithFormat:@"%ld", iteration]];
} else {
int carrier = 0;
for (long long j = arrayOfNumbers.count-1; j > -1; --j) {
int a = [[arrayOfNumbers objectAtIndex:j] intValue];
int b = [[backwardArrayOfNumbers objectAtIndex:j] intValue];
//NSLog(@"a = %i, b = %i", a, b);
int c = a+b+carrier;
if (c > 9) {
c = c-10;
carrier = 1;
} else {
carrier = 0;
}
[nextArrayOfNumbers addObject:[NSString stringWithFormat:@"%i", c]];
if (carrier == 1 && (nextArrayOfNumbers.count == arrayOfNumbers.count)) {
[nextArrayOfNumbers addObject:[NSString stringWithFormat:@"%i", carrier]];
}
//NSLog(@"nextArrayOfNumbers = %@", nextArrayOfNumbers);
}
for (int i = 0; i < nextArrayOfNumbers.count; ++i) {
NSString *back = [nextArrayOfNumbers objectAtIndex: nextArrayOfNumbers.count-(i+1)];
//NSLog(@"back = %@", back);
[nextString appendString:back];
back = NULL;
}
if (iteration%1000 == 0) {
NSLog(@"iteration %ld; count:%u", iteration, nextArrayOfNumbers.count);
}
//NSLog(@"iteration %ld", iteration);
[self iterate:nextString];
}
}
}
以后15,000次迭代,崩溃+错误,没有内存警告:
- (void)didReceiveMemoryWarning
{
NSLog(@"Error near iteration %ld", iteration);
[super didReceiveMemoryWarning];
}
任何想法可能是什么问题?提前谢谢!
编辑:在CString
和NSString
之间转换对ARC来说很痛苦。所以我在循环中使用了@autoreleasepool{}
(而nil
而不是NULL
),这大大减少了内存使用量。我的迭代次数超过了50k。
答案 0 :(得分:1)
因此程序本身在使用那么多内存时会遇到一些问题 - 你可以大大减少这个算法的内存使用量。
无论如何,如果发生在主线程上,你将不会收到内存警告。内存警告是在主线程上发出的,你没有机会处理警告,因为在主线程的运行循环有另一次机会完成其正常工作(例如处理内存警告或处理其他事件)之前耗尽内存。
如果这种情况发生在辅助线程上,也许你会看到不同的东西,但这并不能解决问题的根源。
答案 1 :(得分:0)
你正在递归地解决一个填满内存的问题。
当计算机完成15,000个周期中的每一个周期时,您必须记录下去的地方。这可能会成为很多空间。
如果可以使这个“尾递归”,你可以节省空间。例如:
"bad" recursion which saves in memory 7 + 6 + 5 + 4 + 3 + 2
int factorial (int x)
{
if (x > 1)
{
return (x + recursion (x - 1));
}
else return x;
}
//
good recursion start with y = 1
only saves in memory two integers, updating them every cycle.
int factorial (int x, int y)
{
if (x > 1)
{
return factorial (x - 1, (x * y));
}
else return x;
}