CoreData问题 - 无法识别的选择器设置为实例

时间:2016-05-26 20:50:19

标签: ios objective-c xcode core-data

我从其他人那里继承了一个项目,它是在旧版本的Xcode中创建的。升级后,我发现了一些我必须解决的问题,但这个问题让我感到难过。

我有一个CoreData模型,其中包含由Xcode(NSManagedObject)生成的类。我有一个Meeting对象,其中包含使用Speaker类的speaker属性。这些关系都已到位,但在第一次尝试分配会议实例的发言人属性时,我得到以下内容:

2016-05-26 16:32:46.276 SignMeIn[7829:316171] -[NSKnownKeysDictionary1 setSpeaker:]: unrecognized selector sent to instance 0x7a9042b0
2016-05-26 16:32:46.288 SignMeIn[7829:316171] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[NSKnownKeysDictionary1 setSpeaker:]: unrecognized selector sent to instance 0x7a9042b0'
*** First throw call stack:
(
    0   CoreFoundation                      0x033ea494 __exceptionPreprocess + 180
    1   libobjc.A.dylib                     0x02ea4e02 objc_exception_throw + 50
    2   CoreFoundation                      0x033f4253 -[NSObject(NSObject) doesNotRecognizeSelector:] + 275
    3   CoreFoundation                      0x0332989d ___forwarding___ + 1037
    4   CoreFoundation                      0x0332946e _CF_forwarding_prep_0 + 14
    5   SignMeIn                            0x000be242 +[CoreDataManager addSpeakerWithDictionary:forMeeting:] + 1458
    6   SignMeIn                            0x000bf6b6 +[CoreDataManager insertMeetingsFromArray:] + 902
    7   SignMeIn                            0x000b7f5b -[SyncView request:hasBeenTerminatedWithSuccess:forServiceMethod:] + 2203
    8   SignMeIn                            0x0009c0f6 __91+[OnsiteAttendeeAPI callApiMethod:isPost:parametersDictionary:delegate:shouldStartRequest:]_block_invoke.101 + 118
    9   SignMeIn                            0x00070425 -[ASIHTTPRequest reportFinished] + 213
    10  libobjc.A.dylib                     0x02eb9059 -[NSObject performSelector:withObject:] + 70
    11  Foundation                          0x023eb5f8 __NSThreadPerformPerform + 323
    12  CoreFoundation                      0x032fce5f __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE0_PERFORM_FUNCTION__ + 15
    13  CoreFoundation                      0x032f2aeb __CFRunLoopDoSources0 + 523
    14  CoreFoundation                      0x032f1f08 __CFRunLoopRun + 1032
    15  CoreFoundation                      0x032f1846 CFRunLoopRunSpecific + 470
    16  CoreFoundation                      0x032f165b CFRunLoopRunInMode + 123
    17  GraphicsServices                    0x04a71664 GSEventRunModal + 192
    18  GraphicsServices                    0x04a714a1 GSEventRun + 104
    19  UIKit                               0x00e64eb9 UIApplicationMain + 160
    20  SignMeIn                            0x000534f2 main + 178
    21  libdyld.dylib                       0x040aaa25 start + 1
)
libc++abi.dylib: terminating with uncaught exception of type NSException

我的Meeting类具有Speaker *类型的speaker属性,.m中的所有内容都有@dynamic语句,应该创建getter / setter。

以下是代码:

+ (void) addSpeakerWithDictionary: (NSDictionary *) speakerDict forMeeting: (Meeting *) aMeeting
{
    int speakerID = [speakerDict[@"id"] intValue];
    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"identification = %d AND %@ IN meeting", speakerID, aMeeting];
    NSArray *speakersArray = [CoreDataManager fetchObjects:@"Speaker" withSortDescriptors:nil andPredicate:predicate];

    if (speakersArray.count == 0)
    {
        Speaker *speaker = [NSEntityDescription insertNewObjectForEntityForName:@"Speaker" inManagedObjectContext:[CoreDataManager managedObjectContext]];

        speaker.degree =         speakerDict[@"degree"];
        speaker.firstName =      speakerDict[@"firstName"];
        speaker.identification = @(speakerID);
        speaker.lastName =       speakerDict[@"lastName"];
        speaker.preTitle =       speakerDict[@"preTitle"];
        speaker.version =        speakerDict[@"version"];

        aMeeting.speaker = speaker;

    }

非常感谢任何帮助。谢谢!

编辑:这是调用方法:

+ (void) insertMeetingsFromArray: (NSArray *) meetingsArray
{
    for (NSDictionary *dict in meetingsArray) 
    {
        NSPredicate *predicate = [NSPredicate predicateWithFormat:@"identification = %d AND user = %@", [dict[@"id"] intValue], SessionManagerInstance.loggedUser];
        NSArray *meetArray = [CoreDataManager fetchObjects:@"Meeting" withSortDescriptors:nil andPredicate:predicate];

        if (meetArray.count)
        {
            Meeting *meeting = meetArray[0];
            [CoreDataManager addSpeakerWithDictionary:dict[@"speaker"] forMeeting:meeting];
        }
        else
            [CoreDataManager insertMeetingWithDictionary:dict];
    }

    [CoreDataManager saveContext];
}

+ (void) insertMeetingWithDictionary: (NSDictionary *) dict
{
//    NSLog(@"dict: %@", dict);
    Meeting *meeting = [NSEntityDescription insertNewObjectForEntityForName:@"Meeting" inManagedObjectContext:[CoreDataManager managedObjectContext]];

    meeting.brand =          dict[@"brand"];
    meeting.category =       dict[@"category"];
    meeting.city =           dict[@"city"];
    meeting.closed =         @([dict[@"closed"] boolValue]);
    meeting.date =           [Utilities dateFromDateTime:dict[@"date"]];
    meeting.dateString =     dict[@"dateString"];
    meeting.identification = @([dict[@"id"] intValue]);
    meeting.initiative =     dict[@"initiative"];
    meeting.location =       dict[@"location"];
    meeting.notes =          dict[@"notes"];
    meeting.state =          dict[@"state"];
    meeting.timeZone =       dict[@"timeZone"];
    meeting.title =          dict[@"title"];
    meeting.type =           dict[@"type"];

    [meeting setUser:SessionManagerInstance.loggedUser];

    [CoreDataManager addOrInsertRepWithDictionary:dict[@"rep"] forMeeting:meeting];
    [CoreDataManager addSpeakerWithDictionary:dict[@"speaker"] forMeeting:meeting];
    [CoreDataManager insertGroupsFromArray:dict[@"questiongroups"] forMeeting:meeting];

}

更新了课程:

Meeting.h(在.m中使用@dynamic)

#import <Foundation/Foundation.h>
#import <CoreData/CoreData.h>

@class Attendee, Group, Rep, Speaker, User;

@interface Meeting : NSManagedObject

@property (nonatomic, retain) NSString * brand;
@property (nonatomic, retain) NSString * category;
@property (nonatomic, retain) NSString * city;
@property (nonatomic, retain) NSNumber * closed;
@property (nonatomic, retain) NSDate * date;
@property (nonatomic, retain) NSString * dateString;
@property (nonatomic, retain) NSNumber * identification;
@property (nonatomic, retain) NSString * initiative;
@property (nonatomic, retain) NSString * location;
@property (nonatomic, retain) NSNumber * needsToBeSubmitted;
@property (nonatomic, retain) NSString * notes;
@property (nonatomic, retain) NSString * state;
@property (nonatomic, retain) NSString * timeZone;
@property (nonatomic, retain) NSString * title;
@property (nonatomic, retain) NSString * transactionId;
@property (nonatomic, retain) NSString * type;
@property (nonatomic, retain) NSSet *attendees;
@property (nonatomic, retain) NSSet *groups;
@property (nonatomic, retain) Rep *rep;
@property (nonatomic, retain) Speaker *speaker;
@property (nonatomic, retain) User *user;
@end

@interface Meeting (CoreDataGeneratedAccessors)

- (void)addAttendeesObject:(Attendee *)value;
- (void)removeAttendeesObject:(Attendee *)value;
- (void)addAttendees:(NSSet *)values;
- (void)removeAttendees:(NSSet *)values;
- (void)addGroupsObject:(Group *)value;
- (void)removeGroupsObject:(Group *)value;
- (void)addGroups:(NSSet *)values;
- (void)removeGroups:(NSSet *)values;

@end

Speaker.h(在.m中使用@dynamic)

#import <Foundation/Foundation.h>
#import <CoreData/CoreData.h>


@interface Speaker : NSManagedObject

@property (nonatomic, retain) NSString * degree;
@property (nonatomic, retain) NSString * firstName;
@property (nonatomic, retain) NSNumber * identification;
@property (nonatomic, retain) NSString * lastName;
@property (nonatomic, retain) NSString * preTitle;
@property (nonatomic, retain) NSString * version;
@property (nonatomic, retain) NSSet *meeting;
@end

@interface Speaker (CoreDataGeneratedAccessors)

- (void)addMeetingObject:(NSManagedObject *)value;
- (void)removeMeetingObject:(NSManagedObject *)value;
- (void)addMeeting:(NSSet *)values;
- (void)removeMeeting:(NSSet *)values;

@end

2 个答案:

答案 0 :(得分:0)

提及NSKnownKeysDictionary1几乎肯定意味着这一行:

[CoreDataManager fetchObjects:@"Meeting" withSortDescriptors:nil andPredicate:predicate];

...正在执行获取请求,其结果类型为NSDictionaryResultType。这意味着meetArray[0]是一个字典,而不是一个托管对象。它没有setSpeaker方法,导致您看到的错误。

您可以更改获取请求以返回托管对象,除非您出于某种原因需要将它们作为字典。但你不能使用这样的词典。

答案 1 :(得分:0)

确保当前的Core Data模型具有正确的属性。

我遇到了一个与Core Data类似的问题,我遇到了一个无法识别的选择器,该设置器方法错误。我无意中将当前Core Data模型中的属性重命名为与Core Data类不同的名称。

相关问题