###NSSet和NSDictionary 兩個常用的類,它們預設假定了其中物件的記憶體行為。對於NSSet來說,object是強引用的,和NSDictionary中的value是一樣的。而NSDictionary中的key則是copy的,因此當開發者想要使NSSet的objects或者NSDictionary的values為weak,或者NSDictionary使用沒有實現協議的物件作為key時,比較麻煩(需要使用NSValue的方法valueWithNonretainedObject)。 還好蘋果為我們提供了相對於NSSet和NSDictionary更通用的兩個類NSHashTable和NSMapTable。 NSHashTable是比NSSet更通用的一個相似物。NSHashTable相對於NSSet/NSMutableSet有如下特徵: NSSet/NSMutableSet對其物件是強引用,使用isEqual方法去檢查物件是否相等,使用方法hash去獲取hash值。 NSHashTable是可變的,沒有一個不變的和其對應。 NSHashTable可以對其物件是weak引用。 NSHashTable可以在輸入(加入)的時候copy物件。 NSHashTable可以包含任意指標,使用指標去做相等或者hashing檢查。 如下面一個例子:
NSHashTable *hashTable = [NSHashTable hashTableWithOptions:NSPointerFunctionsCopyIn]; 當然還有很多其他配置,同時也可以這樣: [NSHashTable hashTableWithOptions:NSHashTableObjectPointerPersonality|NSHashTableWeakMemory] [hashTable addObject:@"foo"]; [hashTable addObject:@"bar"]; [hashTable addObject:@"foo"]; [hashTable addObject:@42]; NSLog(@"Members: %@", [hashTable allObjects]);
NSHashTable使用一個option去初始化,下面是可用的選項: NSHashTableStrongMemory:和NSPointerFunctionsStrongMemory相同,使用此選項為預設的行為,和NSSet的記憶體策略相同。 NSHashTableWeakMemory:和NSPointerFunctionsWeakMemory相同,此選項使用weak儲存物件,當物件被銷燬的時候自動將其從集合中移除。 NSHashTableCopyIn:和NSPointerFunctionsCopyIn相同,此選項在物件被加入到集合之前copy它們。 NSHashTableObjectPointerPersonality:和NSPointerFunctionsObjectPointerPersonality相同,此選項是直接使用指標進行isEqual:和hash。 NSMapTable和NSDictionary相對應,相對於NSDictionary/NSMutableDictionary,NSMapTable有如下的特徵: NSDictionary/NSMutableDictionary會copy對應的key,強引用相應的value。 NSMapTable是可變的,沒有一個不變的類與其對應。 NSMapTable可以對其key和value弱引用,在這種情況下當key或者value被釋放的時候,此entry會自動從NSMapTable中移除。 NSMapTable在加入一個(key,value)的時候,可以對其value設定為copy。 NSMapTable可以包含任意指標,使用指標去做相等或者hashing檢查。 下面的NSMapTable例子中,key不是copy的(強引用的),value為弱引用。
id delegate = ...; NSMapTable *mapTable = [NSMapTable mapTableWithKeyOptions:NSMapTableStrongMemory valueOptions:NSMapTableWeakMemory]; [mapTable setObject:delegate forKey:@"foo"]; NSLog(@"Keys: %@", [[mapTable keyEnumerator] allObjects]);
NSMapTable物件在初始化的時候使用options去分別指定keys和values的行為。 NSMapTableStrongMemory:指定對應的key或者value為強引用。NSMapTableWeakMemory:指定對應的key或者value為弱引用。NSMapTableCopyIn:指定對應的key或者value在加入到集合中的時候為copy。 NSMapTableObjectPointerPersonality:此選項是直接使用指標進行isEqual:和hash。