Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>A couple of years ago, I wrote a few category methods for exactly the same reason, transforming a whole tree of user defaults to mutable. Here they are - use them at your own risk! :-)</p> <pre><code>// // SPDeepCopy.h // // Created by Sherm Pendley on 3/15/09. // #import &lt;Cocoa/Cocoa.h&gt; // Deep -copy and -mutableCopy methods for NSArray and NSDictionary @interface NSArray (SPDeepCopy) - (NSArray*) deepCopy; - (NSMutableArray*) mutableDeepCopy; @end @interface NSDictionary (SPDeepCopy) - (NSDictionary*) deepCopy; - (NSMutableDictionary*) mutableDeepCopy; @end </code></pre> <hr> <pre><code>// // SPDeepCopy.m // // Created by Sherm Pendley on 3/15/09. // #import "SPDeepCopy.h" @implementation NSArray (SPDeepCopy) - (NSArray*) deepCopy { unsigned int count = [self count]; id cArray[count]; for (unsigned int i = 0; i &lt; count; ++i) { id obj = [self objectAtIndex:i]; if ([obj respondsToSelector:@selector(deepCopy)]) cArray[i] = [obj deepCopy]; else cArray[i] = [obj copy]; } NSArray *ret = [[NSArray arrayWithObjects:cArray count:count] retain]; // The newly-created array retained these, so now we need to balance the above copies for (unsigned int i = 0; i &lt; count; ++i) [cArray[i] release]; return ret; } - (NSMutableArray*) mutableDeepCopy { unsigned int count = [self count]; id cArray[count]; for (unsigned int i = 0; i &lt; count; ++i) { id obj = [self objectAtIndex:i]; // Try to do a deep mutable copy, if this object supports it if ([obj respondsToSelector:@selector(mutableDeepCopy)]) cArray[i] = [obj mutableDeepCopy]; // Then try a shallow mutable copy, if the object supports that else if ([obj respondsToSelector:@selector(mutableCopyWithZone:)]) cArray[i] = [obj mutableCopy]; // Next try to do a deep copy else if ([obj respondsToSelector:@selector(deepCopy)]) cArray[i] = [obj deepCopy]; // If all else fails, fall back to an ordinary copy else cArray[i] = [obj copy]; } NSMutableArray *ret = [[NSMutableArray arrayWithObjects:cArray count:count] retain]; // The newly-created array retained these, so now we need to balance the above copies for (unsigned int i = 0; i &lt; count; ++i) [cArray[i] release]; return ret; } @end @implementation NSDictionary (SPDeepCopy) - (NSDictionary*) deepCopy { unsigned int count = [self count]; id cObjects[count]; id cKeys[count]; NSEnumerator *e = [self keyEnumerator]; unsigned int i = 0; id thisKey; while ((thisKey = [e nextObject]) != nil) { id obj = [self objectForKey:thisKey]; if ([obj respondsToSelector:@selector(deepCopy)]) cObjects[i] = [obj deepCopy]; else cObjects[i] = [obj copy]; if ([thisKey respondsToSelector:@selector(deepCopy)]) cKeys[i] = [thisKey deepCopy]; else cKeys[i] = [thisKey copy]; ++i; } NSDictionary *ret = [[NSDictionary dictionaryWithObjects:cObjects forKeys:cKeys count:count] retain]; // The newly-created dictionary retained these, so now we need to balance the above copies for (unsigned int i = 0; i &lt; count; ++i) { [cObjects[i] release]; [cKeys[i] release]; } return ret; } - (NSMutableDictionary*) mutableDeepCopy { unsigned int count = [self count]; id cObjects[count]; id cKeys[count]; NSEnumerator *e = [self keyEnumerator]; unsigned int i = 0; id thisKey; while ((thisKey = [e nextObject]) != nil) { id obj = [self objectForKey:thisKey]; // Try to do a deep mutable copy, if this object supports it if ([obj respondsToSelector:@selector(mutableDeepCopy)]) cObjects[i] = [obj mutableDeepCopy]; // Then try a shallow mutable copy, if the object supports that else if ([obj respondsToSelector:@selector(mutableCopyWithZone:)]) cObjects[i] = [obj mutableCopy]; // Next try to do a deep copy else if ([obj respondsToSelector:@selector(deepCopy)]) cObjects[i] = [obj deepCopy]; // If all else fails, fall back to an ordinary copy else cObjects[i] = [obj copy]; // I don't think mutable keys make much sense, so just do an ordinary copy if ([thisKey respondsToSelector:@selector(deepCopy)]) cKeys[i] = [thisKey deepCopy]; else cKeys[i] = [thisKey copy]; ++i; } NSMutableDictionary *ret = [[NSMutableDictionary dictionaryWithObjects:cObjects forKeys:cKeys count:count] retain]; // The newly-created dictionary retained these, so now we need to balance the above copies for (unsigned int i = 0; i &lt; count; ++i) { [cObjects[i] release]; [cKeys[i] release]; } return ret; } @end </code></pre>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload