Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cocoa/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/oracle/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Objective c 示例Cocoa应用程序,参考计数,[池漏]产生EXC\u坏访问?_Objective C_Cocoa_Xcode - Fatal编程技术网

Objective c 示例Cocoa应用程序,参考计数,[池漏]产生EXC\u坏访问?

Objective c 示例Cocoa应用程序,参考计数,[池漏]产生EXC\u坏访问?,objective-c,cocoa,xcode,Objective C,Cocoa,Xcode,我正在研究,在第4章中我写了这个应用程序: int main (int argc, const char * argv[]) { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; //create the date object NSCalendarDate *now = [[NSCalendarDate alloc] init]; //seed random # generator

我正在研究,在第4章中我写了这个应用程序:

int main (int argc, const char * argv[]) {
    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];

    //create the date object
    NSCalendarDate *now = [[NSCalendarDate alloc] init];

    //seed random # generator
    srandom(time(NULL));

    NSMutableArray *array;
    array = [[NSMutableArray alloc] init];
    int i;
    for (i=0; i<10; i++){
        //create a date/time that is 'i' weeks from now
        NSCalendarDate *iWeeksFromNow;
        iWeeksFromNow = [now dateByAddingYears:0
                                        months:0
                                          days:(i*7)
                                         hours:0
                                       minutes:0
                                       seconds:0];

        //create a new instance of lottery entry
        LotteryEntry *entry = [[LotteryEntry alloc] init];
        [entry setEntryDate:iWeeksFromNow];

        [array addObject:entry];
        [entry release];
    }
    [now release];
    now = nil;

    for (LotteryEntry *entryToPrint in array) {
        NSLog(@"%@", entryToPrint);
    }
    [array release];
    array = nil;

    NSLog(@"about to drain the pool... (%@)", pool);
    [pool drain];
    NSLog(@"done");
    NSLog(@"GC = %@", [NSGarbageCollector defaultCollector]);
    return 0;
}
如你所见,我在这里保留和释放对象。我很确定我的代码与这本书的代码相匹配,但是当我运行应用程序时,在[pool drain]我收到以下消息:

程序接收信号: “EXC_坏访问”

我不确定是什么原因造成的。我希望这是我错过的一些愚蠢的事情,但我肯定会感谢其他人对它的关注。提前谢谢


(旁注:我是一名.NET开发人员,所以ref计数对我来说非常陌生!)

doh!仅仅输入代码就让我意识到了我的问题。Doncha喜欢这种情况吗


我在我的
init
中保留了日期,但是我仍然有一个额外的
setEntryDate
方法没有调用retain。删除此项并调用
initWithDate
方法似乎可以解决问题。

这与您手头的问题无关,但您应该避免使用
NSCalendarDate
,它已经被弃用了一段时间,很可能很快就会从API中完全删除。

这种方法似乎也有缺陷:

- (id)initWithDate:(NSCalendarDate *)date
{
    if(![super init])
        return nil;

    NSAssert(date != nil, @"Argument must be non-nil");

    firstNumber = random() % 100 + 1;
    secondNumber = random() % 100 + 1;
    entryDate = [date retain];  
    return self;
}
您实际上是在丢弃[super init]的结果,虽然在本例中这可能不是问题,但在其他情况下可能会导致严重问题。您应该“始终”这样构造您的init方法:

@implementation LotteryEntry

- (void)setEntryDate:(NSCalendarDate *)date
{
    entryDate = date;
}

- (NSCalendarDate *)entryDate
{
    return entryDate;
}

- (int)firstNumber
{
    return firstNumber;
}

- (int)secondNumber
{
    return secondNumber;
}

- (id)init
{
    return [self initWithDate:[NSCalendarDate calendarDate]];
}

- (id)initWithDate:(NSCalendarDate *)date
{
    if(![super init])
        return nil;

    NSAssert(date != nil, @"Argument must be non-nil");

    firstNumber = random() % 100 + 1;
    secondNumber = random() % 100 + 1;
    entryDate = [date retain];  
    return self;
}

- (NSString *)description
{
    NSString *result;
    result = [[NSString alloc] initWithFormat:@"%@ = %d and %d",
              [entryDate descriptionWithCalendarFormat:@"%b %d %Y"],
              firstNumber,
              secondNumber];
    return result;
}

- (void)dealloc
{
    NSLog(@"deallocating %@", self);
    [entryDate release];
    [super dealloc];
}

@end
- (id)initWithDate:(NSCalendarDate *)date
{
    if(self = [super init]) {
        NSAssert(date != nil, @"Argument must be non-nil");

        firstNumber = random() % 100 + 1;
        secondNumber = random() % 100 + 1;
        entryDate = [date retain];
}
return self;
如果您不打算从init方法返回self(例如,它是一个工厂或类似的奇怪的东西),您应该记住释放self。它已经被分配,如果你不归还它,它就不能正常释放。例如:

- (id) init
{
    NSObject*    newSelf = [[NSObject alloc] init];

    [self release];
    return newSelf;
}

请注意,您应该使用NSDate,而不是NSCalendarDate。感谢您提供的提示,这使NSCalendar、NSDate和NSDateComponents变得合理。您可以在此处阅读更多关于它们的信息: