2012-03-27 80 views
0

我正在嘗試將每個核心數據實體的核心數據調用集中到一個助手類中。每個Helper類都包含實體的讀取,更新和插入方法。對於一個實體的輔助類,我得到一個內存泄漏時,我在這條線分析的應用程序:iOS 5.1核心數據內存泄漏

NSArray *results = [managedObjectContext executeFetchRequest:request error:&error]; 

ARC打開並認爲已被卸載後出現的泄漏。

下面是相關聯的ViewController和幫助器類代碼:

ViewController.m

@synthesize location // and other properties...; 

- (void)viewDidLoad 
{ 
    [self loadLocation]; 
    [super viewDidLoad]; 
} 

- (void)viewDidUnload 
{ 
    // Set properties to nil here 

    [super viewDidUnload]; 
} 

- (void)viewDidAppear:(BOOL)animated 
{ 
    [super viewDidAppear:animated]; 
} 

- (void)loadLocation 
{ 
    if (self.locationID.intValue > 0) 
    { 
     LocationCoreDataHelper *helper = [[LocationCoreDataHelper alloc] init]; 
     self.location = [helper selectLocationWithPredicate:[NSString stringWithFormat:@"id = %d", self.locationID.intValue]]; 

     if(self.location) 
     { 
      // Create a new coordinate of the user's location 
      CLLocationCoordinate2D coord; 
      coord.latitude = [self.location.latitude doubleValue]; 
      coord.longitude =[self.location.longitude doubleValue]; 

      // Annotate the point with user's information 
      MKPointAnnotation *point = [[MKPointAnnotation alloc] init]; 
      point.coordinate = coord; 
      point.title = self.location.title; 
      point.subtitle = self.location.subtitle; 

      // Add the annotated point 
      [mkMap addAnnotation:point]; 

      // Set the viewable region of the map 
      MKCoordinateRegion region = MKCoordinateRegionMakeWithDistance(point.coordinate, 5000, 5000); 

      [mkMap setRegion:region animated:YES]; 
     } 

     helper = nil; 
    } 
} 

位置屬性被定義爲實體的管理對象類。

LocationCoreDataHelper.m

@implementation LocationCoreDataHelper 

- (id)init 
{ 
    if(self = [super init]) 
    { 
     // Setup the core data manager if needed 
     if(managedObjectContext == Nil) 
     { 
      managedObjectContext = [(AppDelegate *)[[UIApplication sharedApplication] delegate] managedObjectContext]; 
     }   
    } 

    return self; 
} 

- (Location *)selectLocationWithPredicate:(NSString *)predicateString 
{ 
    NSError *error = nil; 

    // Build the entity and request 
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"Location" inManagedObjectContext:managedObjectContext]; 
    NSFetchRequest *request = [[NSFetchRequest alloc] init]; 
    [request setEntity:entity]; 

    if(predicateString) 
    { 
     // Set the search criteria 
     NSPredicate *predicate = [NSPredicate predicateWithFormat:predicateString]; 
     [request setPredicate:predicate]; 
    } 

    // Perform the search 
    // LEAK HERE 
    NSArray *results = [managedObjectContext executeFetchRequest:request error:&error]; 

    if(results.count >0) 
    { 
     return (Location *)[results lastObject]; 
    } 
    else 
    { 
     return nil; 
    } 
} 

// Other methods here 
@end 

我想不通爲什麼內存泄漏發生在那裏。有任何想法嗎?

更新#1:

如果我替換此:

point.coordinate = coord; 
point.title = self.location.title; 
point.subtitle = self.location.subtitle; 

與此:

point.coordinate = coord; 
point.title = @"Title"; 
point.subtitle = @"Subtitle"; 

NSLog(@"%@", self.location.title); 

我不明白的內存泄漏。這是爲什麼?

+1

聽起來像一個保留週期:讓'point.title'和'point.subtitle'弱引用? – lnafziger 2012-03-28 02:47:46

+0

你有沒有試過打開靜態分析儀? – Pochi 2012-03-28 02:55:58

+0

@Inafziger:如何讓MKPointAnnotation的Title和SubTitle屬性成爲弱引用? – Joshua 2012-03-28 03:03:56

回答

0

感謝Inafziger指引我在正確的方向。我最後不得不創建一個自定義MKAnnotation類,像這樣:

#import <Foundation/Foundation.h> 
#import <MapKit/MapKit.h> 

@interface MyAnnotation : NSObject <MKAnnotation> 

@property (nonatomic, readonly) CLLocationCoordinate2D coordinate; 
@property (nonatomic, copy, readonly) NSString *title; 
@property (nonatomic, copy, readonly) NSString *subtitle; 

- (id) initWithCoordinates:(CLLocationCoordinate2D)paramCoordinates 
        title:(NSString *)paramTitle 
        subTitle:(NSString *)paramSubTitle; 

@end 

,我更新了我的視圖控制器像這樣:

MyAnnotation *point = [[MyAnnotation alloc] initWithCoordinates:coord 
                  title:self.location.title 
                 subTitle:self.location.subtitle]; 

通過以這種方式實現自定義註解類,它解決了問題的內存泄漏。我仍然不能100%確定儀器爲什麼將漏洞指向核心數據呼叫。也許因爲那是NSManagedObject的起源,那不正確的發佈?