Reputation: 187
All,
I have created a datamodel with 3 field:
- beingPlayed type int16
- position type int16
- playedBy type int16
I have generated a class for it.
Tile.h
@property (nonatomic, retain) NSNumber * beingPlayed;
@property (nonatomic, retain) NSNumber * playedBy;
@property (nonatomic, retain) NSNumber * position;
Tile.m
@dynamic beingPlayed;
@dynamic playedBy;
@dynamic position;
I would assume that all 3 variables are NSNumbers and have the type int16 (CFNumberType = kCFNumberSInt16Type).
When I create the Tile object, I set all parameters to 0 with[NSNumber numberwithint:0]
But when I want to set another value for this object, the type of beingPlayed is not set and so the value is not correct.
I have used:
self.beingPlayed = self.playedBy = self.position = [NSNumber numberWithInt:175];
Result:
position = 175
playedBy = 175
beingPlayed = -81
I have used:
self.playedBy = self.position = [NSNumber numberWithInt:175];
self.beingPlayed = self.position;
Result:
position = 175
playedBy = 175
beingPlayed = -81
When I debug, I see that:
- position has type kCFNumberSInt16Type
- playedBy has type kCFNumberSInt32Type
- beingPlayed has NO type....
What is going on here? Where can I set the type or where is the type set?
My issue is that it's now a normal int which can only contain values < 127, but I have set the type in the datamodel to int16....
Edit:
Additional code from OP from comments:
Tile *newTile = [NSEntityDescription
insertNewObjectForEntityForName:@"Tile" inManagedObjectContext:context];
newTile.playedBy = @(129);
newTile.position = @(129);
newTile.beingPlayed = @(129);
[context save:&error];
Logging: playedBy = -127, position = 129 and beingPlayed = 129
Upvotes: 0
Views: 285
Reputation: 187
The
"Also, make sure that you are not overriding any getters or setters that could potentially also change the result."
did the trick! I had a method (BOOL)isBeingPlayed which is also part of the KVC implementation and therefor one of the setters/getters... It slipped my mind.
And because a BOOL is also an int in basic, the type was converted to an int instead of the int16....
Thank you all for your help!
Upvotes: 0
Reputation: 80265
Here is what you need to understand: the generated NSManagedObject
subclasses use objects for all numbers rather than primitives. It is also possible to use primitives, but there are some advantages to leaving things the way the Xcode editor creates them.
In short you need to understand that an object in C is just a pointer to this object. So the value of this pointer is irrelevant for you. The SDK provides obvious methods to wrap and unwrap NSNumber
objects.
// set
position = @3994;
// get
NSInteger p1 = position.integerValue;
int p2 = position.intValue;
BOOL p3 = position.boolValue;
// modify
position = @(position.integerValue + 1);
// compare
position.integerValue == position2.integerVaue // true if equal
Your chained assignments don't work because of the different meaning of =
when dealing with objects vs. values.
NSNumber *x, *y;
x = @1; // assign value to x
y = x; // y points to x
Also, make sure that you are not overriding any getters or setters that could potentially also change the result.
Upvotes: 1