On my Lion app, I have this data model:
The relationship subitems
inside Item
is ordered.
Xcode 4.1 (build 4B110) has created for me the file Item.h
, Item.m
, SubItem.h
and SubItem.h
.
Here is the content (autogenerated) of Item.h
:
#import <Foundation/Foundation.h>
#import <CoreData/CoreData.h>
@class SubItem;
@interface Item : NSManagedObject {
@private
}
@property (nonatomic, retain) NSString * name;
@property (nonatomic, retain) NSOrderedSet *subitems;
@end
@interface Item (CoreDataGeneratedAccessors)
- (void)insertObject:(SubItem *)value inSubitemsAtIndex:(NSUInteger)idx;
- (void)removeObjectFromSubitemsAtIndex:(NSUInteger)idx;
- (void)insertSubitems:(NSArray *)value atIndexes:(NSIndexSet *)indexes;
- (void)removeSubitemsAtIndexes:(NSIndexSet *)indexes;
- (void)replaceObjectInSubitemsAtIndex:(NSUInteger)idx withObject:(SubItem *)value;
- (void)replaceSubitemsAtIndexes:(NSIndexSet *)indexes withSubitems:(NSArray *)values;
- (void)addSubitemsObject:(SubItem *)value;
- (void)removeSubitemsObject:(SubItem *)value;
- (void)addSubitems:(NSOrderedSet *)values;
- (void)removeSubitems:(NSOrderedSet *)values;
@end
And here is the content (autogenerated) of Item.m
:
#import "Item.h"
#import "SubItem.h"
@implementation Item
@dynamic name;
@dynamic subitems;
@end
As you can see, the class Item
offers a method called addSubitemsObject:
. Unfortunately, when trying to use it in this way:
Item *item = [NSEntityDescription insertNewObjectForEntityForName:@"Item" inManagedObjectContext:self.managedObjectContext];
item.name = @"FirstItem";
SubItem *subItem = [NSEntityDescription insertNewObjectForEntityForName:@"SubItem" inManagedObjectContext:self.managedObjectContext];
[item addSubitemsObject:subItem];
this error appear:
2011-09-12 10:28:45.236 Test[2002:707] *** -[NSSet intersectsSet:]: set argument is not an NSSet
Can you help me?
Update:
After just 1,787 days from my bug report, today (August 1, 2016) Apple wrote me this: "Please verify this issue with the latest iOS 10 beta build and update your bug report at bugreport.apple.com with your results.". Let's hope this is the right time :)
I think everybody is missing the real problem. It is not in the accessor methods but rather in the fact that
NSOrderedSet
is not a subclass ofNSSet
. So when-interSectsSet:
is called with an ordered set as argument it fails.fails with
*** -[NSSet intersectsSet:]: set argument is not an NSSet
Looks like the fix is to change the implementation of the set operators so they handle the types transparently. No reason why a
-intersectsSet:
should work with either an ordered or unordered set.The exception happens in the change notification. Presumably in the code that handles the inverse relationship. Since it only happens if I set an inverse relationship.
The following did the trick for me
Yes, this is definitely a Core Data bug. I wrote up an ObjC-Runtime-based fix a while back, but at the time I figured it would be fixed soon. Anyway, no such luck, so I posted it up on GitHub as KCOrderedAccessorFix. Work around the problem on all your entities:
One entity in particular:
Or just for one relationship:
Instead to making a copy I suggest to use the accessor in NSObject to get access to the NSMutableOrderedSet of the relationships.
e.g. the Core Data Release Notes for iOS v5.0 refer to this.
In a short test it worked in my application.
Better version of the correct answer in SWIFT
The Apple docs To Many Relations says: you should access the proxy mutable set or ordered set using
Modifying this set will add or remove relations to your managed object. Accessing the mutable ordered set using the accessor whether with [ ] or . notation is wrong and will fail.
If you are using mogenerator, then instead of
simply use: