2013-05-24 2 views
0

У меня есть UITableView с некоторыми данными. У каждой ячейки есть кнопка, и если вы нажмете ее, вы удалите выбранную ячейку. После этого я должен сохранить свои данные с помощью NSUserDefault. Вот некоторые код:плохой доступ после синхронизации NSUserDefault

- (void)buttonPressed:(UIButton *)sender{ 
    int tag=sender.tag; 
    [myArray removeObjectAtIndex:tag]; 

    [self saveData]; 
    [self.myTableView reloadData]; 
} 

метод buttonPressed вызывает saveData метод:

-(void)saveData{ 
    dataString=[[NSString alloc]init]; //defined in .h file 

    for(int i=0; i<([myArray count]); i++){ 
     ClassObject *aObject=[[ClassObject alloc]init]; 
     aObject=[myArray objectAtIndex:i]; 
     dataString=[dataString stringByAppendingString:aObject.idObject]; 
     dataString=[dataString stringByAppendingString:@"$"]; 
     dataString=[dataString stringByAppendingString:aObject.description1]; 
     dataString=[dataString stringByAppendingString:@"$"]; 
     dataString=[dataString stringByAppendingString:aObject.description2]; 
     dataString=[dataString stringByAppendingString:@"?"]; 
     [aObject release]; 
    } 


    NSUserDefaults *dataDefault=[NSUserDefaults standardUserDefaults]; 
    [dataDefault setObject:dataString forKey:@"myDataString"]; 
    [dataDefault synchronize]; 
    [dataString release]; 
} 

в режиме отладки все идет хорошо, пока метод saveData не заканчивается. Когда он заканчивает отладочные возвраты по методу buttonPressed, он перезагружает табличное представление, а затем приложение сбой. И я не знаю, почему.

Некоторые идеи? Благодарю.

+0

происходит ли он в любой строке кода, который вы указываете там? на строке '' reloadData'' или сразу после возврата из метода '' ButtonPressed''? –

+0

Возможно, вам стоит опубликовать свой код делегата datasource, похоже, что там происходит сбой. – Marcel

+0

@MichaelDautermann он сработает после того, как метод «buttonPressed» закончен. сразу после последнего '}' – gabboSonc

ответ

1

Где aEquipaggio происходит из вашего приложения saveData? Почему вы выпускаете его на каждой итерации цикла? Это не имеет смысла, и это, скорее всего, слишком поздно, что приведет к сбою позже.

Edit: Теперь, когда вы изменили код в ваш вопрос, aEquipaggio больше не существует, но release в конце цикла все еще неправильно, и первая строка в цикле совершенно бессмысленно (и утечки), потому что вы никогда не используете экземпляр ClassObject, который вы выделяете.

Вы также не должны выпускать dataString в конце метода. В этот момент dataString больше не содержит тот же экземпляр, что и вы в alloc - init в начале, потому что вы заменили его экземпляром с автореализацией в цикле. ([[NSString alloc]init] бессмысленно в любом случае, просто используйте @"").

+0

мой плохой, я собираюсь редактировать XD – gabboSonc

0

Дикая догадка, может быть, это как-то связано с освобождением dataString. Попробуйте его оптимизировать.

1
ClassObject *aObject=[[ClassObject alloc]init]; 
aObject=[arrayEquipaggio objectAtIndex:i]; 
// ... 
[aObject release]; 

Firstly, and most importantly, it's rather anObject.

Во-вторых, это и утечек памяти (вы потеряете указатель на выделенную, например, когда вы переназначить [arrayEquipaggio objectAtIndex:i]; к переменной) и над-релизах aObject (который теперь, как я просто объяснил, указывает на объект внутри массива, поэтому вы освобождаете объект, который у вас нет).

В общем, удалите строку с Alloc-INIT и что с выходом (вы делаете ту же самую ошибку с dataString переменной тоже) и:

Read this before continuing with development! Иначе вы будете иметь серьезные проблема с чем-либо в Objective-C. В настоящее время вы, похоже, не знаете, как работает управление памятью. (Также было бы полезно изучить C, прежде чем пытаться использовать Objective-C, но, к сожалению, это слишком большое ожидание ...)

+0

спасибо, но я мог бы назвать его aobject или bobject или cobject. «a» не является статьей – gabboSonc

+0

@gabboSonc ОК, тогда остальная часть ответа по-прежнему применяется (и в любом случае лучшим соглашением об именах будет «objectA» и т. д. в этом случае), вы должны позаботиться о указателях вы не пропускаете и не перезапускаете объекты. –

+0

так, как я могу изменить свой код, чтобы исправить проблему? – gabboSonc

1

У вас неправильное распределение памяти. Это то, что вы делаете:

dataString = [[NSString alloc] init]; 
dataString = [dataString stringByAppendingString:@"$"]; 
[dataString release]; 

Сначала вы назначаете новую строку, которую вы должны выпустить позже. Ничего страшного. Затем вы сохраняете другой указатель на переменную dataString, протекая предыдущую строку.И затем вы освобождаете строку с автореализацией, создаваемую -stringByAppendingString, так что вскоре после этого объект будет высвобожден.

Смежные вопросы