Reputation: 41
I have a NSManagedObject in my iOS app. This object is called a Round. In the Round I have a to-many relationship to a bunch of Person objects.
xCode generates my managed object class using NSSet as the data type of my to-many relationship to Person managed objects.
So my Round managed object looks like this right:
@interface Round : NSManagedObject
{
}
@property (nonatomic, retain) NSSet* people;
@end
However NSSet is not an ordered collection and I want to retain the ordering of a NSArray I'm using to hold these Person objects as I assign it to my Round managed object.
I tried just converting my NSArray to NSSet, however the original ordering of the set is not retained.
I tried changing the type from NSSet to NSArray in my Round managed object by got the following error at runtime.
2011-03-11 14:00:06.950 SkeetTracker[42782:207] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: **'Unacceptable type of value for to-many relationship: property = "people"; desired type = NSSet; given type = __NSArrayM;** value = ( " (entity: Person; id: 0x5bed0c0 ; data: {\n firstName = Todd;\n lastName = McFarlane;\n round = \"0x5bf2cb0 \";\n scores = \"\";\n})",
Has anyone ever encountered such a thing and know of a solution?
Kind Regards, George
Upvotes: 4
Views: 3431
Reputation: 2860
I believe that iOS 5 actually has built it in - but regardless, if you want a persistent sorted ordering, you need to have a stored attribute that you can create an NSSortDescription
from. Then you add one more method (I prefer a readonly property so I can dot-access it too) which returns the [NSSet sortedArrayUsingDescriptors:self.unsortedSetMethod]
array.
Upvotes: 3
Reputation: 49
Thx for the great idea. I think in my case I can just add an "index" property to the elements of my array (they're managed objects also) and make the index a transient property.
I was a little unclear why you needed to create the extra transient array attribute.
Upvotes: 0
Reputation: 39915
This is kind of a complex thing to do, and I wish Apple would build it in. But since they haven't, you have to use a workaround. What I usually do is use a transient attribute with an undefined type, and add an index attribute to the elements in the array. When the data is loaded, you create an array, which is the transient attribute, using the objects sorted by their index. When the context is saved, you go through the array and make sure each object has the correct index. Alternatively, if there are few changes, you can change the index whenever you change the array.
Upvotes: 2