0

I have a time sensitive section of my code which stores, retrieves, and replaces values in an NSMutableDictionary. The problem is that I need to store objects, not primitives, and objects need to be allocated on the heap. However, once there exists an object in the dictionary and I want to replace the value, instead of allocating another number, can't I simply replace the current heap literal, wherever it may be, with the new int?

Problem is, I have been storing NSNumbers and I cannot change the value of an NSNumber because they are immutable.

Currently, I use the @() wrapper operator to create an NSNumber, which I believe must be copied to the heap to be stored in the dictionary.

-(void)setInt: (int)value For: (NSString *)key {
    [self.dictionary setValue:@(value) forKey:key];
}

I would imagine that replacing an object's primitive in C would be easy:

-(void)setInt: (int)value For: (NSString *)key {
    SomeMutableIntClass * oldValue;
    oldValue = (SomeMutableIntClass *) [self.dictionary objectForKey:key];
    oldValue.int = value; // Direct copy like a pointer since int is primitive
}

I am wondering if I should just make an Integer class with one int property. Even if I went about making my own class would this actually be faster and require less allocing that my current code?

Community
  • 1
  • 1
Timothy Swan
  • 623
  • 3
  • 9
  • 21
  • Correct. Your solution would be "faster". But it might not make your program noticeably-to-the-user faster - only profiling can show that. – Colin Aug 05 '14 at 17:06

1 Answers1

0

I use the @() wrapper operator to create an NSNumber, which I believe must be copied to the heap to be stored in the dictionary.

This is correct.

I would imagine that replacing an object's primitive in C would be easy:

That is correct too. Unfortunately, since NSNumber is immutable, you need to write your own SomeMutableIntClass.

Even if I went about making my own class would this actually be faster and require less allocing that my current code?

Adding mutability may help, but the answer depends on the values that you store in your mutable dictionary. If you keep storing the same numbers over and over, you may be getting cached instances of your wrappers, without additional allocations.

Note: your current program assumes that all keys will be present in the dictionary. If this is not true, you would need to add nil checking of oldValue to your setInt: method.

Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • A friend recommended doing away with the dictionary and creating runtime properties for some object [during runtime](http://nshipster.com/associated-objects/). He said it would even be faster than a dictionary. Would this work well? How would I code it? – Timothy Swan Aug 05 '14 at 20:17
  • @TimothySwan Associating objects does not work for primitives, so you would end up with `NSNumber` wrappers again. Associated objects are using the same dictionary behind the scene, so I wouldn't expect too much improvement of the execution speed. Apart from that, the article that you linked describes the process well. – Sergey Kalinichenko Aug 05 '14 at 20:23
  • Are you sure we are talking about associated objects the same way? I would create one generic object which would act as the dictionary, and dynamically add properties to it. The property names would be the keys. The values can be primitive ints, right? – Timothy Swan Aug 06 '14 at 00:55
  • @TimothySwan There needs to be a container that "maps" object addresses to their associated objects. Since all this is happening at runtime, the things that `objc_getAssociatedObject` can return are all references, not primitives. So you would need to use `NSNumber` anyway. – Sergey Kalinichenko Aug 06 '14 at 01:47
  • I have a value class with properties that hold primitives. Even if I have to allocate one of those, I can alter its primitive values later. – Timothy Swan Aug 06 '14 at 07:45