Авто-релиз в приложении Objective-C при возврате значения - PullRequest
0 голосов
/ 27 ноября 2010

Я прочитал руководство по управлению памятью для языка Objective-C, но это сомнение у меня остается, даже после прочтения этой главы много раз.

Допустим, я хочу вернуть объект, который я только что создал, в методе объекта, подобного этому:

NSString* ret = [[NSString alloc] initWithString:@"My string"];
return ret;

Я могу сделать это, но это не правильно в соответствии с политикой собственности. В руководстве говорится, что правильным решением будет:

NSString* ret = [[NSString alloc] initWithString:@"My string"];
return [ret autorelease];

потому что, поскольку я авто-релиз, я больше не владелец. Мой вопрос: когда NSString будет действительно освобожден и освобожден? Когда будет выпущен последний инициализированный пул? Это означает, что, если я не создаю пул, этот объект будет освобожден при закрытии приложения (пул, который xcode создает по умолчанию, освобождается в конце). Это правильно? То же самое относится к объектам, которые не выделены мной, например:

NSString* ret = [NSString stringWithString:@"My string"];

? Если я не создаю пул, чтобы выпустить его в другом месте, он освобождается в конце приложения при освобождении пула, созданного с помощью xcode? Спасибо за любые разъяснения.

Ответы [ 3 ]

2 голосов
/ 27 ноября 2010

Объекты попадают в текущий пул автоматического выпуска, когда они автоматически освобождены.Когда сам пул отправляется release (или drain, что тоже самое), объекты в нем также отправляются release.Что касается того, когда текущий пул автоматического выпуска будет создаваться и освобождаться в большинстве случаев, глава руководства по управлению памятью об автоматическом выпуске гласит:

Application Kit автоматически создает пул в начале цикла событий (илиитерации цикла события), например событие нажатия мыши, и освобождает его в конце

Таким образом, на практике автоматически освобожденные объекты исчезают очень быстро - до конца срока службы приложения ифакт перед отправкой следующего сообщения о событии touch / mouseMoved.

Можно создать свой собственный локальный пул автоматического выпуска, чтобы они могли уйти еще быстрее, если это необходимо, но обычно это микрооптимизация, которая может на самом делезаставляет дела идти немного медленнее (это увеличивает количество отправляемых сообщений без необходимости заставлять что-либо еще занимать меньше времени).

2 голосов
/ 27 ноября 2010

Когда вы звоните autorelease, вы передаете свое право собственности в ближайший пул автоматического выпуска, который будет освобожден при следующем сливе.

Всегда должен быть самый внешний пул авто-релиза, но обычно есть другие, ближе к действию. Вам не нужно создавать их явно - хотя вы тоже можете это делать - они создаются платформой Cocoa в процессе работы программы.

Если вы кодируете инструмент без графического интерфейса, который никогда не переключается на платформу, и вы никогда не создаете другой пул и никогда не вызываете drain для существующего, тогда объект будет освобожден, когда сам пул будет Перед выходом. В противном случае он чаще всего освобождается в конце цикла обработки событий, что является одним из ключевых мест, в которых платформа поддерживает пул.

В общем случае, объекты, созданные с помощью методов удобного класса, совпадают с теми, которые были выделены и автоматически выпущены. Как это бывает, тот, который вы цитируете из NSString, будет немного отличаться, потому что в его основе находится строка constant , и это не совсем так управляется. Но это детали реализации.

1 голос
/ 27 ноября 2010

Имейте в виду, что -autorelease - это не что иное, как средство отложенного обмена сообщениями.Когда вы отправляете -autorelease объекту, текущий пул автоматического выпуска добавит этот объект в свой список, а когда пул будет освобожден или освобожден, он отправит сообщение -release каждому объекту в его списке.

...