我已经构建了一个在iOS 5.1,6.0和6.1上运行的简单琐事游戏。我使用Core Data,我有这两个对象:
@interface Category : NSManagedObject
@property (nonatomic, retain) NSString * category;
@property (nonatomic, retain) NSNumber * difficulty;
@property (nonatomic, retain) NSSet *questions;
@end
和
@interface Question : NSManagedObject
@property (nonatomic, retain) NSNumber * disabled;
@property (nonatomic, retain) NSNumber * displayTypeEasy;
@property (nonatomic, retain) NSNumber * displayTypeHard;
@property (nonatomic, retain) NSNumber * displayTypeMedium;
@property (nonatomic, retain) NSNumber * questionID;
@property (nonatomic, retain) Category *category;
@end
这个想法是每个问题只有一个类别(比如娱乐或体育)。类别 - 问题关系是一对多的;在我的样本数据中,有3个类别和20个问题。
我有一个设置窗口,允许用户更改他们想要播放的类别和/或更改给定类别的难度级别(即在此窗口中,对类别对象进行更改)。当用户按下OK时,执行以下代码:
- (IBAction)okPressed:(UIButton *)sender {
NSError * error;
BOOL wasSaveSuccessful = [[Constants database].managedObjectContext save:&error];
NSLog(@"wasSaveSuccessful:%@ areChangesPending:%@", wasSaveSuccessful ? @"YES" : @"NO",
[[Constants database].managedObjectContext hasChanges] ? @"YES" : @"NO");
}
顺便说一句:“[常量数据库]”是一个代表我的持久存储的UIManagedDocument。不可否认,这可能不是保持这种情况的最好方法,但我不相信这是我问题的根源。
接下来,用户可以按下新游戏按钮。然后执行此提取:
- (void) loadBatchOfQuestions
{
if ([self.questionBatch count] == 0) { // self.questionBatch is an NSMutableArray
// TEST #1
for (Category * c in [[Category allCategories] objectEnumerator])
NSLog(@"category:%@ difficulty:%d", c.category, [c.difficulty integerValue]);
// TEST #2
Question * q1 = [Question queryQuestionWithQuestionID:50150];
NSLog(@"q1 difficulty:%d", [q1.category.difficulty integerValue]);
NSFetchRequest * request = [NSFetchRequest fetchRequestWithEntityName:@"Question"];
request.predicate = [NSPredicate predicateWithFormat:
@"(disabled == NO)"
@"AND (questionID > %ld)"
@"AND (((category.difficulty == %i) AND (displayTypeEasy != NULL))"
@" OR ((category.difficulty == %i) AND (displayTypeMedium != NULL))"
@" OR ((category.difficulty == %i) AND (displayTypeHard != NULL)))",
MAX_QUESTIONID_FOR_TEST_QUESTIONS,
DIFFICULTY_EASY, DIFFICULTY_MEDIUM, DIFFICULTY_HARD];
NSError * error;
[self.questionBatch addObjectsFromArray:[[Constants database].managedObjectContext executeFetchRequest:request error:&error]];
}
问题在于:如果在按下确定并离开设置窗口后,我等了大约10秒才按下新游戏,一切都很好; loadBatchOfQuestions中的fetch根据当前的Category数据返回正确的行。但是,如果我在关闭设置窗口后立即按下新游戏,我会看到旧数据(即我查询错误的问题)。
对于我在上面添加的NSLog语句:
然而,后续的提取会返回旧数据。
以下是我认为正在发生的事情:
我的问题: