gpt4 book ai didi

objective-c - 获取一对多核心数据关系第一次返回正确的对象,但其他时间返回空集

转载 作者:行者123 更新时间:2023-11-29 13:36:11 25 4
gpt4 key购买 nike

我有一个对象 Workout,它与一个对象 Exercise 具有一对多关系。

模型图:http://i.imgur.com/q1Mfq.png

当我创建一个 Workout 对象时,我通过循环将三个 Exercise 对象添加到它

[self addExercisesObject:exercise]

然后保存我的托管对象上下文。然后,从用于显示锻炼的 Controller 中,我可以成功获取锻炼及其练习(使用获取请求),如我的调试器中的输出所示:

Printing description of self->_savedWorkout:
<Workout: 0x6c5a990> (entity: Workout; id: 0x6e46e00 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/Workout/p1> ; data: {
bodyweight = nil;
date = "2012-05-09 16:59:43 +0000";
exercises = (
"0x6e3c870 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/Exercise/p3>",
"0x6e3eaf0 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/Exercise/p2>",
"0x6e36820 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/Exercise/p1>"
);
isCompleted = 0;
workoutId = 1;
workoutPlan = "0x6e6c980 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/WorkoutPlan/p1>";
})

到目前为止一切顺利。但是,如果我在我的模拟器中关闭我的应用程序并再次启动它并在同一 View 中执行相同的获取请求,则锻炼看起来像这样:

Printing description of self->_savedWorkout:
<Workout: 0x6ea8ff0> (entity: Workout; id: 0x6e8f9e0 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/Workout/p1> ; data: {
bodyweight = nil;
date = "2012-05-09 16:59:43 +0000";
exercises = (
);
isCompleted = 0;
workoutId = 1;
workoutPlan = "0x6c8a130 <x-coredata://EA417EAA-101A-4F04-8276-3C4A6CDF094D/WorkoutPlan/p1>";
})

它似乎获取了相同的锻炼对象,但现在锻炼是一个空集。实际上,在获取请求之后,练习首先看起来像这样:

exercises = "<relationship fault: 0x8a93100 'exercises'>";

但是一旦我这样做了:

for (Exercise *exercise in self.savedWorkout.exercises)

self.savedWorkout.exercises 解析为空集。我不会在我的应用程序的任何部分以任何方式编辑锻炼。

我的获取请求是通过我的 Workout 类中的此方法发出的:

- (Workout *)getLatestWorkout
{
self.model = [[self.managedObjectContext persistentStoreCoordinator] managedObjectModel];

NSFetchRequest *fetchRequest = [self.model fetchRequestTemplateForName:@"getLatestWorkout"];

NSError *error = nil;
NSArray *results = [self.managedObjectContext executeFetchRequest:fetchRequest error:&error];
if ([results count] == 1) {
return [results objectAtIndex:0];
}
return nil;
}

我使用 Xcode 的 GUI 工具制作了获取请求模板。它在 isCompleted == 0 处获取所有 Workout 对象。您可以看到它每次都获取相同的对象,因为锻炼的 x-coredata 路径在两个调试器输出中是相同的。

更新:我检查了我的 SQLite 数据库。锻炼表中有一项锻炼,练习表中有三项练习。

有什么想法吗?

编辑:创建下面发布的对象的代码

<p></p>

<pre><code>- (void)storeUserSettings
{
// get the file path if it exists
NSString *path = [[NSBundle mainBundle] pathForResource:@"userSettings" ofType:@"plist"];

// create it if it doesn't
if (path == nil) {
path = [NSString stringWithFormat:@"%@%@",
[[NSBundle mainBundle] bundlePath], @"/userSettings.plist"];
}

// and write the new settings to file
[self.userSettings writeToFile:path atomically:YES];

// load managed object context
[self loadMOC];

WorkoutPlan *currentPlan = [[WorkoutPlan alloc] getActiveWorkoutPlan];

[currentPlan setManagedObjectContext:self.managedObjectContext];

// if user has no plan or is changing plans, create new plan and first workout
if (currentPlan == nil ||
([self.userSettings valueForKey:@"plan"] != currentPlan.planId)) {

// create a workoutPlan object
WorkoutPlan *workoutPlan = [[WorkoutPlan alloc] initWithEntity:
[NSEntityDescription entityForName:@"WorkoutPlan"
inManagedObjectContext:self.managedObjectContext]
insertIntoManagedObjectContext:self.managedObjectContext];

// set attributes to values from userSettings and save object
[workoutPlan createWorkoutPlanWithId:[self.userSettings valueForKey:@"plan"]
schedule:[self.userSettings valueForKey:@"schedule"]
dateStarted:[self.userSettings valueForKey:@"nextDate"]];
}
// if user is just changing schedule, update schedule of current plan
else if (![currentPlan.schedule isEqualToString:[self.userSettings valueForKey:@"schedule"]]) {
[currentPlan setSchedule:[self.userSettings valueForKey:@"schedule"]];

[currentPlan saveMOC];
}
}

- (void)loadMOC
{
AppDelegate *delegate = (AppDelegate*)[[UIApplication sharedApplication] delegate];
self.managedObjectContext = delegate.managedObjectContext;
self.model = [[self.managedObjectContext persistentStoreCoordinator] managedObjectModel];
}

- (void)createWorkoutPlanWithId:(NSNumber *)planId schedule:(NSString *)schedule
dateStarted:(NSDate *)dateStarted
{
[self deactivateCurrentPlan];

// set workout plan attributes
[self setPlanId:planId];
[self setIsActive:[NSNumber numberWithBool:YES]];
[self setSchedule:schedule];
[self setDateStarted:dateStarted];

// create first workout and add to workout plan

Workout *firstWorkout = [NSEntityDescription
insertNewObjectForEntityForName:@"Workout"
inManagedObjectContext:self.managedObjectContext];

[firstWorkout setManagedObjectContext:self.managedObjectContext];

[firstWorkout createFirstWorkoutForPlan:self onDate:dateStarted];

[self addWorkoutsObject:firstWorkout];

[self saveMOC];
}

- (void)createFirstWorkoutForPlan:(WorkoutPlan *)plan onDate:(NSDate *)startDate
{
// set workout attributes
[self setDate:startDate];
[self setIsCompleted:[NSNumber numberWithBool:NO]];
[self setWorkoutId:[NSNumber numberWithInt:1]];

NSArray *exerciseList = [self getExercisesForWorkout:self inPlan:plan];

// iterate over exercises in spec and create them
for (NSDictionary *exerciseSpec in exerciseList)
{
// create a exercise MO
Exercise *exercise = [NSEntityDescription
insertNewObjectForEntityForName:@"Exercise"
inManagedObjectContext:[plan managedObjectContext]];

[exercise setManagedObjectContext:[plan managedObjectContext]];
[exercise createExerciseForWorkout:self withSpec:exerciseSpec];

// add exercise to workout object
[self addExercisesObject:exercise];
}

}

- (void)createExerciseForWorkout:(Workout *)workout withSpec:exerciseSpec
{
// set exercise attributes
self.exerciseId = [exerciseSpec valueForKey:@"id"];
self.isPersonalRecord = [NSNumber numberWithBool:NO];

NSArray *sets = [exerciseSpec valueForKey:@"sets"];
int i = 1;
for (NSNumber *setReps in sets)
{
// create a set MO
Set *set = [NSEntityDescription
insertNewObjectForEntityForName:@"Set"
inManagedObjectContext:[workout managedObjectContext]];

[set setManagedObjectContext:[workout managedObjectContext]];

// set set attributes
set.order = [NSNumber numberWithInt:i];
set.repetitions = setReps;
set.weight = [exerciseSpec valueForKey:@"default_weight"];

// add set to exercise object
[self addSetsObject:set];
i++;
}
}
</code></pre>

<p></p>

最佳答案

我遇到了类似的问题。父子关系在应用程序运行时有效,但在重新启动后仅检索到最新的子记录。

我是这样添加 child 的:

  • 创建子记录
  • 设置 child 的parent属性,设置 child 的other属性
  • 使用父级的添加方法将子级添加到父级

我发现如果我这样做是固定的:

  • 创建子记录
  • 使用父级的添加方法将子级添加到父级
  • 设置 child 的parent属性,设置 child 的other属性

关于objective-c - 获取一对多核心数据关系第一次返回正确的对象,但其他时间返回空集,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10522250/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com