Я создал графическое приложение, которое вызывает веб-службу. Пользователь может масштабировать и перемещать график, и программа время от времени принимает решение о вызове веб-службы для получения дополнительных данных. Это достигается следующим процессом:
Граф имеет цикл рендеринга, который постоянно отображает граф, и некоторую логику принятия решений, которая добавляет информацию о вызовах веб-службы в стек.
Отдельный поток берет самую последнюю информацию о вызове веб-службы из стека и использует ее для выполнения вызова веб-службы. Остальные объекты в стеке помещаются в корзину.
Идея этого состоит в том, чтобы уменьшить количество вызовов веб-службы только теми, которые подходят, и только по одному за раз.
Правильно, без длинной истории (за что я извиняюсь), вот моя проблема с управлением памятью:
График имеет постоянные (и соответствующим образом заблокированные) объекты NSDate* для текущего отображаемого времени начала и окончания графика. Они передаются в инициализаторы для моих объектов запроса веб-службы. Затем объекты вызова веб-службы сохраняют даты.
После того, как вызовы веб-службы были выполнены (или помещены в корзину, если они устарели), они выпускают файл NSDate*.
Сам график выпускает и перераспределяет новые NSDates * по событию «завершение касания».
Если при вызове removeAllObjects в стеке находится только один объект вызова веб-службы, EXC_BAD_ACCESS возникает в методе освобождения объекта вызова веб-службы, когда он пытается освободить объекты даты (даже если они кажутся существующими и находятся в области действия в отладчике). .
Если, однако, я закомментирую сообщения об освобождении от деструктора, утечки памяти не произойдет для одного освобождаемого объекта в стеке, но утечка памяти произойдет, если в стеке более одного объекта.
Я абсолютно не понимаю, что происходит не так. Не имеет значения, какую симантику хранения я использую для дат объектов вызова веб-службы, поскольку они назначаются в инициализаторе, а затем только для чтения (поэтому для корректности установлено значение только для чтения).
Также не имеет значения, сохраняю ли я или копирую даты в инициализаторе (хотя все остальное, очевидно, выходит за рамки или нежелательно выпускается в другом месте и вызывает сбой).
Извините, что это объяснение длинное, надеюсь, оно достаточно ясное, но, боюсь, я тоже не играю на этом. Большое спасибо всем, кто может помочь, даже предложить что-нибудь, что я, возможно, пропустил?
Чтобы, надеюсь, немного прояснить ситуацию, вот некоторый псевдо(иш) код... вещи (исключая блокировки и инициализаторы):
NSMutableArray* requests;
NSDate* start, end;
-(void)webServiceThread
{
if([requests count] > 1)
{
[self doRequestWithParams:[requests lastObject]];
[requests removeAllObjects];
}
}
-(void)render
{
if(conditions for another web service call are met)
{
WebServiceRequest* new = [[WebServiceRequest alloc] initWithDates:start :end];
[requests addObject:new];
[new release];
}
[self doRendering];
}
-(void)touchesEnded
{
[start release];
[end release];
start = [[NSDate dateSinceTimeInterval:chartLeft] retain]; //Ficticious NSDate Method names for example.
end = [[NSDate dateSinceTimeInterval:chartRight] retain];
}
А затем в объекте вызова веб-службы:
NSDate* startDate;
NSDate* endDate;
-(void)initWithDates:start :end
{
startDate = [start retain];
endDate = [end retain];
}
-(void)dealloc
{
[super dealloc];
//The following two lines cause EXC_BAD_ACCESS if this is the only object on the request stack. If they are commented, however, memory is leaked if this is not the only object on the request stack.
[startDate release];
[endDate release];
}