2013-04-11 72 views
0

我有一組Videos對象,其中包括屬性idtags建立一對多關係的最佳方式是什麼?

我想要建立一個字典,其keytag和其valueid的數組。

例如,一些Video對象可能是這樣的:

Video{ id:1, tags:[funny,political,humor] }

Video{ id:2, tags:[political,america] }

我想要的結果字典是這樣的:

VideosWithTags["funny":[1]; "political":[1,2]; "humor":[1]; "america":[2]]

有一個標準算法來完成這個?

目前我在做這樣的事情:

for (NSDictionary *video in videos) 
{ 
    NSNumber *videoId = [video objectForKey:@"id"]; 
    NSArray *tags = [video objectForKey:@"tags"]; 

    for (NSString *tag in tags) 
    { 
     NSMutableArray *videoIdsForTag = nil; 

     if ([videosAndTags objectForKey:tag] != nil) //same tag with videoIds already exists 
     { 
      videoIdsForTag = [videosAndTags objectForKey:tag]; 
      [videoIdsForTag addObject:videoId]; 

      //add the updated array to the tag key 
      [videosAndTags setValue:videoIdsForTag forKey:tag]; 
     } 
     else //tag doesn't exist yet, create it and add the videoId to a new array 
     { 
      NSMutableArray *videoIds = [NSMutableArray array]; 
      [videoIds addObject:videoId]; 

      //add the new array to the tag key 
      [videosAndTags setObject:videoIds forKey:tag]; 
     } 
    } 
} 
+0

這代碼看上去完全合理的我。你覺得有什麼需要改進的地方嗎?重構它會容易一點點,但它不會明顯改變性能。 – 2013-04-11 15:36:47

+0

不是特別的,比任何事情都更好奇。 – 2013-04-11 15:44:33

回答

1

您可以通過使用新的文本語法這看起來有點清潔。

我認爲你可以通過讓if分支做更少的工作而受益。例如你會試圖獲取videoIds數組,那麼如果它不存在更好 - 創建它,並把它添加到videosAndTags對象,然後在該點之後的代碼可以不重邏輯

for (NSDictionary *video in videos) { 
    NSNumber *videoId = video[@"id"]; 
    NSArray *tags = video[@"tags"]; 

    for (NSString *tag in tags) { 
    NSMutableArray *videoIds = videosAndTags[tag]; 
    if (!videoIds) { 
     videoIds = [NSMutableArray array]; 
     videosAndTags[tag] = videoIds; 
    } 

    // This is the only line where I manipulate the array 
    [videoIds addObject:videoId]; 
    } 
} 
+0

不錯。這是我正在尋找的。不知道這些文字! – 2013-04-11 15:45:40

1
NSArray* videos = 
    @[@{ @"id" : @1, @"tags" : @[ @"funny", @"political", @"humor" ] }, 
     @{ @"id" : @2, @"tags" : @[ @"political", @"america" ] } ]; 
NSMutableDictionary* videosAndTags = [NSMutableDictionary new]; 

// find distinct union of tags 
NSArray* tags = [videos valueForKeyPath: @"@distinctUnionOfArrays.tags"]; 

// for each unique tag 
for(NSString* tag in tags) 
{ 
    // filter array so we only have ones that have the right tag 
    NSPredicate* p = [NSPredicate predicateWithFormat: @"tags contains %@", tag]; 
    videosAndTags[ tag ] = [[videos filteredArrayUsingPredicate: p] valueForKeyPath: @"id"]; 
} 
一致

這是另一種使用NSPredicate和valueForKeyPath的方法。

我不使用他們經常,但有時他們可以證明是有用的。

(我認爲他們稱之爲事物的函數式編程風格,但我不是很確定)

NSPredicate reference
Key Value Coding

相關問題