0

iOS 7 アプリに Core Data を実装しようとしています (以前は成功していました)。しかし、executeFetchRequest メソッドを実行すると、アプリがクラッシュします。最も関連性の高いコードを以下に追加します。

#import "JTHuntingSeasonDB.h"

@implementation JTHuntingSeasonDB

- (id)init {
    self = [super init];
    if (self) {
        NSFileManager *fileManager = [NSFileManager defaultManager];
        NSURL *documentsDirectory = [[fileManager URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] firstObject];

        NSString *documentName = @"JTHuntingDB";
        NSURL *url = [documentsDirectory URLByAppendingPathComponent:documentName];

        document = [[UIManagedDocument alloc] initWithFileURL:url];


        BOOL fileExists  = [[NSFileManager defaultManager] fileExistsAtPath:[url path]];

        if (fileExists) {
            [document openWithCompletionHandler:^(BOOL success) {
                if (success) {
                    NSLog(@"Document opened successfully");
                    self.allSpecies = [self getSpecies];
                    self.speciesToday = [self getSpeciesToday];
                } else NSLog(@"Failed to open document");
            }];
        } else {
            [document saveToURL:url forSaveOperation:UIDocumentSaveForCreating completionHandler:^(BOOL success) {
                if (success)  {
                    NSLog(@"Document created successfully");
                    self.allSpecies = [self getSpecies];
                    self.speciesToday = [self getSpeciesToday];
                }  else NSLog(@"Failed to create document, path: %@", url);
            }];
        }
    }

    return self;
}

#pragma mark - Core Data

- (NSArray *)getSpecies {
    if (document.documentState == UIDocumentStateNormal) {
        context = document.managedObjectContext;

        NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
        NSString *country = [defaults stringForKey:@"Country"];
        NSString *subregion = [defaults stringForKey:@"Subregion"];

        NSFetchRequest *request = [NSFetchRequest fetchRequestWithEntityName:@"HuntingDates"];
        NSSortDescriptor *sortDescriptor = [NSSortDescriptor sortDescriptorWithKey:@"name" ascending:YES selector:@selector(localizedStandardCompare:)];
        request.fetchBatchSize = 150;
        request.fetchLimit = 150;
        request.sortDescriptors = @[sortDescriptor];

        if (subregion.length > 0) {
            request.predicate = [NSPredicate predicateWithFormat:@"(country IN %@) AND (subregion IN %@)", country, subregion];
        } else {
            request.predicate = [NSPredicate predicateWithFormat:@"country IN %@", country];
        }

        NSError *error;
        return [context executeFetchRequest:request error:&error];
    }

    return nil;
}

この線

return [context executeFetchRequest:request error:&error];

アプリがクラッシュする原因となります。これは私がこれまでに行って発見したことです:

  • シミュレーター: アプリを削除し、コンテンツと設定をリセットしました
  • Xcode: クリーン (ビルド フォルダー)
  • 「コンテキスト」は nil ではありません
  • NSLog は「ドキュメントが正常に作成/開かれました」と出力します
  • アプリがクラッシュすると、コンソールに「lldb」のみが出力されます

編集: Wain のアドバイスに従って、例外ブレークポイントをオフにすると、述語が無効であるというよりわかりやすいエラー メッセージが表示されました。述語の IN を CONTAINS に置き換え、変数 "country" を変更して nil を返さないようにすることで問題を解決しました。

4

2 に答える 2