0

I have an instance of NSNumber * did inside a class called Reservation. Below myres is an instance of Reservation

myres.did = [[NSNumber alloc] initWithInt:[[[data objectForKey:@"discount"] did] intValue]];

When I do this everything works just fine. However the code is ugly, and when I do:

myres.did = [data objectForKey:@"discount"] did];

My code breaks down.. I know that [[data objectForKey:@"discount"] did] returns an object, which is an NSNumber.

Can some explain to me why is this? and what do I need to change in my code if I want to assign a NSNumber with another NSNumber?

aherlambang
  • 14,290
  • 50
  • 150
  • 253

3 Answers3

1

Where does the code break down? Do you have a crash happening in your application?

By the way, in the second example, you have a mismatched set of square brackets.

On a conceptual level, the first code example puts a retained object into myres.did, but the second example puts an autorelease object into myres.did. If you later do a release on myres.did by using the second code snipped, you will probably get a crash.

BP.
  • 10,033
  • 4
  • 34
  • 53
0

First ensure that your object's property is set to retain:

@property (nonatomic, retain) NSNumber *did;

and that you are releasing that object in your dealloc.

Unfortunately the copy you have in place cannot become any shorter. What you are in effect doing with this statement:

myres.did = [[NSNumber alloc] initWithInt:[[[data objectForKey:@"discount"] did] intValue]];

is taking the integer value from one NSNumber reference and moving it into another. The integer contents, being non-referential (assign), can move this way. The NSNumber itself cannot be copied as it is immutable. Please see this post for more info. You must have another issue within your code, perhaps an inappropriate release.

Matt Bishop
  • 1,010
  • 7
  • 18
  • If memory mgmt is done correctly, it's perfectly OK to store a reference and retain the same NSNumber object in 'myres'. If 'data' is later deallocated and releases that NSNumber object, the NSNumber itself should not be deallocated unless there is a bug somewhere else. @jlehr is correct that this "copy" tactic is just masking (clumsily) some other memory mgmt bug. – Firoze Lafeer Mar 25 '11 at 04:38
  • Incidentally, [NSNumber numberWithInt:[someOtherNSNumber intValue]] doesn't necessarily return a different instance. For example, currently on the Mac for integers < about 12, you'll actually get the same instance back. – Firoze Lafeer Mar 25 '11 at 04:50
-1

Please see this supplemental answer which gives background to the copying of NSNumber.

Community
  • 1
  • 1
Matt Bishop
  • 1,010
  • 7
  • 18
  • I am still getting an error, is that copy thing the same as doing an initwithint? when you copy do you actualy do an alloc or are we assuming that the left side has been alloc – aherlambang Mar 24 '11 at 02:29
  • `NSNumber` instances are immutable, so sending it a `copy` message is the same as sending it `retain`. `NSNumber`'s `copy` implementation doesn't actually create a copy; instead it returns `self`. – jlehr Mar 24 '11 at 02:51
  • 2
    The proposed solution is wrong, and is masking a more serious memory management bug. The OP should post the declaration of the `did` property. In all likelihood the memory management semantic is `assign`, but should be changed to `retain`. – jlehr Mar 24 '11 at 03:00
  • I think Matt Bishop is right, so I vote up. The original poster's myres.did is assigned a whole new NSNumber. He want a short statement instead, and this solution answered. – AechoLiu Mar 24 '11 at 04:20
  • I actually have it as @property (nonatomic, retain) NSNumber *did; – aherlambang Mar 24 '11 at 04:56
  • @Matt Bishop: Please reread my previous comment. If you think it's incorrect, consider writing an example to test your theory. If you're unsure how, try this: 1. Write a line of code that creates an instance of `NSNumber` and stores a reference in a local variable. 2. On another line, send a `copy` message to the number instance, and store the return value in a second variable. 3. Call `NSLog` to print the addresses stored in the two variables. Notice that the addresses are the same, ergo `copy` didn't copy the object, and in fact is the same as `retain` for immutable objects in Foundation. – jlehr Mar 25 '11 at 03:41