nsmutadedictionaryのメモリリーク、nsxmlparserのnsarray
-
16-09-2019 - |
質問
XMLドキュメントの1つを解析する悪いメモリリークに苦しんでいます。
NSXMLParserを使用して各ノード(以下のXMLサンプルのアルバム)を反復し、各写真ノードを反復し、結果をNSARRAYに追加します。
各ループに2つの値を保存する2つの保持プロパティがあります。これらの値は、各写真ノードを含む別のNSARRAYとともに、NSMUTABLEDICTIONARYオブジェクトに追加されます。結果の辞書は、アプリケーションの他の場所で使用されるNSARRAYに追加されます。
アプリケーションの特定のポイントでXMLドキュメントをリロードするボタンがあります。次に呼ばれるのは、漏れが発生しているときです。 InstrumentsはNSCFARRAYとNSCFSTRINGが漏れていることを示しており、DidendElementに表示されています。
一体どこで私は間違っています。どんなアドバイスでも役立ちます。
- (void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict
{
if([elementName isEqualToString:@"photo"]){
self.strPhotoPath = [attributeDict objectForKey:@"iphone"];
}else if ([elementName isEqualToString:@"album"]) {
dicItem = [[[NSMutableDictionary alloc] init] autorelease];
self.strCurrentTitle = [attributeDict objectForKey:@"band_name"];
self.strCurrentLocation = [attributeDict objectForKey:@"location"];
}
}
- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName
{
if([elementName isEqualToString:@"photo"]){
[self.arrPhotos addObject:self.strPhotoPath];
}else if ([elementName isEqualToString:@"album"]) {
[dicItem setObject:self.strCurrentTitle forKey:@"album"];
[dicItem setObject:self.strCurrentLocation forKey:@"location"];
[dicItem setObject:[self.arrPhotos copy] forKey:@"photos"];
[self.arrAlbums addObject:dicItem];
[self.arrPhotos removeAllObjects];
}
}
これがXMLの切り取りです。
<albums type='array'>
<album location='Album 1' date='2009-12-04 22:47:48 UTC' album_name='' band_name='Band 1'>
<photo display_on_website='true' standard='/system/photos/3396/original/Photo1-DSC8894.jpg' thumb='/system/photos/3396/thumb/Photo1-DSC8894.jpg' date='2009-12-04 22:47:48' exif_data='NIKON D300, F:2.8, Shutter:1/80, Focal:15mm, ISO:1600' iphone='/system/photos/3396/iPhone/Photo2-DSC8894.jpg' available_for_print='false'/>
<photo display_on_website='true' standard='/system/photos/3403/original/Photo2-DSC9146.jpg' thumb='/system/photos/3403/thumb/Photo3-DSC9146.jpg' date='2009-12-04 23:19:27' exif_data='NIKON D300, F:4.5, Shutter:1/160, Focal:70mm, ISO:1600' iphone='/system/photos/3403/iPhone/Photo3-DSC9146.jpg' available_for_print='false'/>
</album>
<album location='Album 2' date='2009-12-04 22:47:48 UTC' album_name='' band_name='Band 2'>
<photo display_on_website='true' standard='/system/photos/3396/original/Photo3-DSC8894.jpg' thumb='/system/photos/3396/thumb/Photo3-DSC8894.jpg' date='2009-12-04 22:47:48' exif_data='NIKON D300, F:2.8, Shutter:1/80, Focal:15mm, ISO:1600' iphone='/system/photos/3396/iPhone/Photo3-DSC8894.jpg' available_for_print='false'/>
<photo display_on_website='true' standard='/system/photos/3403/original/Photo4-DSC9146.jpg' thumb='/system/photos/3403/thumb/Photo4-DSC9146.jpg' date='2009-12-04 23:19:27' exif_data='NIKON D300, F:4.5, Shutter:1/160, Focal:70mm, ISO:1600' iphone='/system/photos/3403/iPhone/Photo4-DSC9146.jpg' available_for_print='false'/>
<photo display_on_website='true' standard='/system/photos/3403/original/Photo5-DSC9146.jpg' thumb='/system/photos/3403/thumb/Photo5-DSC9146.jpg' date='2009-12-04 23:19:27' exif_data='NIKON D300, F:4.5, Shutter:1/160, Focal:70mm, ISO:1600' iphone='/system/photos/3403/iPhone/Photo5-DSC9146.jpg' available_for_print='false'/>
</album>
</albums>
解決
[dicItem setObject:[self.arrPhotos copy] forKey:@"photos"];
このラインは犯人だと思います。コピーは自動化またはリリースされることはなく、パーサーが遭遇するたびに交換されます album
エレメント。使用する:
[dicItem setObject:[[self.arrPhotos copy] autorelease] forKey:@"photos"];
配列のコピーを作成しているため、配列内のすべてのオブジェクトも保持数を増やします。したがって、配列が到達できなくなった場合(辞書で上書きすることで)、アレイが含むすべての文字列がリリースされません適切に、そしてどちらも配列ではありません。
所属していません StackOverflow