0

我有一个 2 标签应用程序。在第一个中,我正在创建“Sample”和“SampleList”实体的对象。每个 sampleList 包含一个 ID 和一组样本。每个样本都包含一个日期和温度属性。

在第二个选项卡中,我在 tableView 中显示我的数据。我实施了

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath

方法以删除 SampleLists。在我xcdatamodel的 SampleList 和 Sample 之间的关系的删除规则中是Cascade.

我的问题是,当我尝试删除刚刚创建的 SampleList 时,应用程序崩溃并且我收到一个EXC_BAD_ACCESS信号。如果我重新启动它,那么我可以毫无问题地删除“旧”样本列表。

早些时候,我遇到了以下问题:我无法显示自启动应用程序以来创建的示例列表,因为它也崩溃了。我也收到了EXC_BAD_ACCESS信号。实际上,该集合的最后一个样本的创建日期似乎是nil。如果我没有发布我用来设置样本日期的 NSDate,我就不会有这个问题了......

如果有人可以帮助我找出可能导致我的麻烦的原因,那就太好了!

这是我用来创建新实例的方法:

SampleList *newSampleList = (SampleList *)[NSEntityDescription insertNewObjectForEntityForName:@"SampleList" inManagedObjectContext:managedObjectContext];
[newSampleList setPatchID:patchID];
NSMutableSet *newSampleSet = [[NSMutableSet alloc] init];
NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];

for (int i = 0; i < [byteArray count]; i=i+4, sampleCount++) {
  NSDateComponents *comps = [[NSDateComponents alloc] init];
  [comps setYear:year];
  [comps setMonth:month];
  [comps setDay:day];
  [comps setHour:hours];
  [comps setMinute:minutes];
  NSDate *sampleDate = [gregorian dateFromComponents:comps];

  Sample *newSample = (Sample *)[NSEntityDescription insertNewObjectForEntityForName:@"Sample" inManagedObjectContext:managedObjectContext];  

  [newSample setSampleDate:sampleDate];
  [newSample setSampleTemperature:[NSNumber numberWithInt:temperature]];

  [newSampleSet addObject:newSample];
  [comps release];
  //[sampleDate release];
 }

 [newSampleList setSampleSet:newSampleSet];
 // [newSampleSet release];

 NSError *error;
 if (![managedObjectContext save:&error]) {
  NSLog(@"Could not Save the context !!");
 }

 [gregorian release];

编辑: 我发现我的错误。我正在对每个 sampleDate 进行比较,如下所示:

NSDate *maxDate = [[NSDate alloc] initWithTimeIntervalSinceReferenceDate:0];
(...)
for (int i = 0; i < [byteArray count]; i=i+4, sampleCount++) {
    (...)
    if ([maxDate compare:sampleDate] == NSOrdredAscending){
        max = sampleDate;
    }

我应该在哪里做:

if ([maxDate compare:sampleDate] == NSOrdredAscending){
    [maxDate release];
    maxDate = [sampleDate retain];
}
4

2 回答 2

1

根据NSEntityDescription的文档,

+ (id)insertNewObjectForEntityForName:(NSString *)entityName inManagedObjectContext:(NSManagedObjectContext *)context

返回一个自动释放的对象。所以你不需要在之后释放它:

[newSampleList setSampleSet:newSampleSet];

newSampleList 最终将被自动释放,这导致您在重新启动应用程序时有时会看到 EXC_BAD_ACCESS。

Apple 的内存管理文档将为您提供何时需要自己释放对象以及何时自动释放对象的最佳实践。

于 2010-06-01T09:45:14.537 回答
0

我喜欢使用如下方法来获取更多信息的 Core Data 错误报告:

- (void) detailedStoreError:(NSError *)error {
    NSLog(@"Failed to save to data store: %@", [error localizedDescription]);
    NSArray *_detailedErrors = [[error userInfo] objectForKey:NSDetailedErrorsKey];
    if (_detailedErrors != nil && [_detailedErrors count] > 0) {
        for (NSError *_detailedError in _detailedErrors) {
            NSLog(@" DetailedError: %@", [_detailedError userInfo]);
        }
    }
    else {
        NSLog(@" %@", [error userInfo]);
    }
}

您可以按如下方式使用它:

NSError *error;
if (![managedObjectContext save:&error]) {
    [self detailedStoreError:error];
}

提供更多信息的错误报告可能会帮助您进行故障排除。

于 2010-06-01T07:57:34.760 回答