Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ios/103.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios pushViewController内存泄漏,并且(我认为)从GCD队列返回_Ios_Memory Management_Viewcontroller_Grand Central Dispatch - Fatal编程技术网

Ios pushViewController内存泄漏,并且(我认为)从GCD队列返回

Ios pushViewController内存泄漏,并且(我认为)从GCD队列返回,ios,memory-management,viewcontroller,grand-central-dispatch,Ios,Memory Management,Viewcontroller,Grand Central Dispatch,我的一个视图控制器出现内存泄漏问题。在我的主视图控制器中,我按下设置视图控制器,如下所示: -(IBAction)launchSettings { SettingsViewController *svc = [[SettingsViewController alloc] init]; svc.title = @"title of app"; //this actually adds a back button for the next vc pushed sel

我的一个视图控制器出现内存泄漏问题。在我的主视图控制器中,我按下设置视图控制器,如下所示:

-(IBAction)launchSettings {
    SettingsViewController *svc = [[SettingsViewController alloc] init];
    svc.title = @"title of app";

    //this actually adds a back button for the next vc pushed
    self.navigationItem.backBarButtonItem = [[[UIBarButtonItem alloc] initWithTitle:@"Back" style:UIBarButtonItemStylePlain target:nil action:nil] autorelease];

    [[self navigationController] pushViewController:svc animated:YES]; // <--Instruments says leak is here
    [svc release];

    if (AdsAreEnabled) {
        ADBannerView *adBanner = SharedAdBannerView;
        adBanner.delegate = nil;
    }    
}
这是我调用GCD的代码,在
设置视图控制器
查看加载期间调用它自己的方法:

if ([iapManager canMakePurchases]) {
    // Display a store to the user.
    iapTableView.sectionFooterHeight = 0;
    iapTableView.rowHeight = 50;
    iapTableView.scrollEnabled = NO;
    //init sectionNames here to avoid leakage.
    sectionNames = [[NSArray alloc] initWithObjects:@"Get Rid of Ads!", nil];
    [spinner startAnimating];
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(reloadStore) name:kInAppPurchaseManagerProductsFetchedNotification object:iapManager];
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(reloadStore) name:kTransactionCompleted object:iapManager];
    //Run this in seperate thread to avoid UI lockup
    dispatch_queue_t store_check = dispatch_queue_create("see if store is available", NULL);
    dispatch_async(store_check, ^ {
        [iapManager loadStore];
    });
    dispatch_release(store_check); 
}
我有点困惑,我在这里做错了什么-我使用完全相同的技术加载不同的视图控制器,它不会泄漏,我不知道如何判断我的GCD东西是否/在哪里泄漏-所有东西都经过反复分析,结果都是干净的。我在SVC的
dealloc
中将我的观察者从通知中心移除,所以不是这样。我确保在我的IAP经理的
dealloc
中删除了事务观察者,所以不是这样

有什么建议吗?你还需要知道些什么来帮助我找出我在这里犯了如此严重的错误

编辑添加:我在SVC的
dealloc
方法中发布了sectionNames,所以也不是这样

编辑2:我尝试了自动释放svc,当我释放它时(并去除相应的释放),但我仍然得到同样的泄漏。

首先,在“启动设置”中。您已经通过“alloc和init”初始化了uibarbuttonite,这使得它的retain count=1,但您还没有释放它

您应该意识到这些属性保留了传递给它们的值。因此,您可以将其自动删除

我应该说,这个动作是不需要的,因为后退按钮已经为您设置好了


其次,在上一个代码片段中,您做了相同的
部分sname

好吧,我最终在朋友的一些故障排除帮助下解决了这个问题-出于某种原因,我忘记了您仍然必须
发布
一个
IBOutlet
ivar,即使您没有将它设置为
属性
(出于某种原因,我认为一个
IBOutlet
autoreleased
,如果它不是一个属性,这是不正确的),一旦我在
dealloc
中获得了适当的释放,我所有的泄漏就神奇地消失了

嗯。我想我的白痴清单上还有一件事要补充。:)


谢谢你们的建议,伙计们

sectionNames
是泄漏,请先调用release或使用属性,然后使用自动释放的数组。记住
viewDidLoad
可以多次调用。不,没有骰子。我在
dealloc
中发布了
sectionNames
,因为在加载显示存储的tableView的其余部分时,我需要再次访问它,但出于某种原因,我只使用了ivar而不是属性。我把它作为一个属性添加了进来,看看它是否修复了它,一开始它看起来像修复了一样,但是没有,仍然会泄漏。这并不能解决你的问题,但这仍然是一个泄漏,即使你在
dealoc
中释放它,你仍然需要在再次分配它之前释放它。我有点困惑——就我所见,只分配了一次,就在这里。然后,当我重新加载tableView的数据时,我只需再次访问它(此时,它只是为
UITableViewStyleGrouped
tableView的sectionHeader读取。如果稍后我给它一个不同的名称,我会释放它,但我只是在这里给它一个名称,这样当存储加载正在旋转时,当我有一个旋转器时,这个名称就会显示出来。嗨,莫汉纳德,实际上,uibarbuttonite是already
autoreleased
,如果你看那行代码的末尾。我这样做是为了让它实际上读“Back”,而不是上一个视图控制器的默认标题(相当长).我还将在
dealloc
中添加一条关于发布sectionNames的注释,因为我这样做了,这似乎是一些人认为的问题所在。
if ([iapManager canMakePurchases]) {
    // Display a store to the user.
    iapTableView.sectionFooterHeight = 0;
    iapTableView.rowHeight = 50;
    iapTableView.scrollEnabled = NO;
    //init sectionNames here to avoid leakage.
    sectionNames = [[NSArray alloc] initWithObjects:@"Get Rid of Ads!", nil];
    [spinner startAnimating];
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(reloadStore) name:kInAppPurchaseManagerProductsFetchedNotification object:iapManager];
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(reloadStore) name:kTransactionCompleted object:iapManager];
    //Run this in seperate thread to avoid UI lockup
    dispatch_queue_t store_check = dispatch_queue_create("see if store is available", NULL);
    dispatch_async(store_check, ^ {
        [iapManager loadStore];
    });
    dispatch_release(store_check); 
}