Просмотр использования памяти в iOS
Есть ли способ узнать, сколько памяти доступно в iOS? Я знаю, что система будет передавать предупреждения с низкой памятью, когда доступная память станет низкой. Тем не менее, у моего приложения есть некоторые моменты, когда один поток выполняет сложную задачу, и иногда эта задача использует достаточное количество памяти, которое просто прекращается ОС (мое приложение может загружать изображения из Интернета, и я масштабирую их до небольшого размер... если пользователь загружает очень большое изображение, у моего приложения заканчивается память и просто идет "poof" ).
Наличие спонтанного завершения приложения, очевидно, является плохим пользовательским интерфейсом.
Есть ли способ, который я могу узнать, когда у меня закончится нехватка памяти и остановите задачу?
Я полагаю, что я мог бы поставить задачу на отдельный поток, и, возможно, система отправила основной поток предупреждение о низкой памяти, но это кажется довольно сложным и даже гарантированным не работает.
Спасибо!
Рон
Ответы
Ответ 1
Во время тестирования и отладки вашего приложения с помощью XCode вы можете использовать эту функцию logMemUsage()
для NSLog используемого/свободного места и следить за тем, как все происходит во время тестирования вашего приложения. Эта функция регистрирует любые изменения в использовании > 100 кб. Он выводится в журнал отладки, как это (на симуляторе свободное пространство огромно):
2011-11-02 21:55:58.928 hello[971:207] Memory used 21884.9 (+21885), free 1838366.8 kb
2011-11-02 21:55:59.936 hello[971:207] Memory used 28512.3 (+6627), free 1830809.6 kb
2011-11-02 21:56:01.936 hello[971:207] Memory used 28803.1 ( +291), free 1830129.6 kb
2011-11-02 21:56:02.936 hello[971:207] Memory used 29712.4 ( +909), free 1830142.0 kb
Вы решаете, где вызывать logMemUsage
в своем приложении. У меня, случается, есть функция, вызываемая таймером каждую секунду, и поэтому я помещаю ее туда. Я предлагаю использовать #ifdef
вокруг них, поэтому этот код включен только в сборки Debug.
#import "mach/mach.h"
vm_size_t usedMemory(void) {
struct task_basic_info info;
mach_msg_type_number_t size = sizeof(info);
kern_return_t kerr = task_info(mach_task_self(), TASK_BASIC_INFO, (task_info_t)&info, &size);
return (kerr == KERN_SUCCESS) ? info.resident_size : 0; // size in bytes
}
vm_size_t freeMemory(void) {
mach_port_t host_port = mach_host_self();
mach_msg_type_number_t host_size = sizeof(vm_statistics_data_t) / sizeof(integer_t);
vm_size_t pagesize;
vm_statistics_data_t vm_stat;
host_page_size(host_port, &pagesize);
(void) host_statistics(host_port, HOST_VM_INFO, (host_info_t)&vm_stat, &host_size);
return vm_stat.free_count * pagesize;
}
void logMemUsage(void) {
// compute memory usage and log if different by >= 100k
static long prevMemUsage = 0;
long curMemUsage = usedMemory();
long memUsageDiff = curMemUsage - prevMemUsage;
if (memUsageDiff > 100000 || memUsageDiff < -100000) {
prevMemUsage = curMemUsage;
NSLog(@"Memory used %7.1f (%+5.0f), free %7.1f kb", curMemUsage/1000.0f, memUsageDiff/1000.0f, freeMemory()/1000.0f);
}
}
Ответ 2
Фактически каждый контроллер представления имеет - (void)didReceiveMemoryWarning
функции.
- (void)didReceiveMemoryWarning
{
// Releases the view if it doesn't have a superview.
[super didReceiveMemoryWarning];
// Release any cached data, images, etc that aren't in use.
}
Как указано в комментариях, вы можете опубликовать неиспользуемые данные в комментарии. С другой стороны, закомментируйте [super didReceiveMemoryWarning];
для подавления предупреждений памяти и объектов автоматического выпуска.
Ответ 3
Во-первых, заголовок вашего вопроса - это то, как смотреть использование памяти в iOS. Существует инструмент, называемый инструментом, который поставляется с xcode, который вы можете использовать для отслеживания распределения памяти, утечек, использования процессора и множества других вещей. См. Apple documentation по этому вопросу..
- Теперь, чтобы увидеть использование памяти в реальном времени вашего приложения, вы можете использовать
инструмент распределителя в приборе
- Чтобы идентифицировать утечки памяти, вы можете использовать инструмент утечки в инструменте.
Также в WWDC 2010 существует video, как анализировать память с помощью инструмента..
Ответ 4
Я рекомендую проверить инструмент обзора Nimbus для просмотра статистики устройств в режиме реального времени. Из коробки он включает страницы для просмотра доступной памяти, дискового пространства и журналов, а также изменения уровней журналов. Также легко добавлять пользовательские страницы, которые показывают любую информацию, которую вы хотите.
http://latest.docs.nimbuskit.info/NimbusOverview.html
![Nimbus' Overview Tool]()
Ответ 5
Набор инструментов для разработки, которые Apple предоставляет, включает "Инструменты". Вы можете использовать это для мониторинга распределения и утечек. В Xcode, если вы долго нажимаете кнопку "Выполнить", вы увидите опцию "Профиль". Это автоматически откроет инструменты и позволит вам выбрать профиль для мониторинга вашего приложения.
Ответ 6
Я люблю бесплатный код. Спасибо прогрм, очень полезно. Пора мне начать делиться воспоминаниями. Я объектно ориентировал его для собственного использования.
#import "mach/mach.h"
#import "memusage.h"
@implementation memusage
static long prevMemUsage = 0;
static long curMemUsage = 0;
static long memUsageDiff = 0;
static long curFreeMem = 0;
-(vm_size_t) freeMemory {
mach_port_t host_port = mach_host_self();
mach_msg_type_number_t host_size = sizeof(vm_statistics_data_t) / sizeof(integer_t);
vm_size_t pagesize;
vm_statistics_data_t vm_stat;
host_page_size(host_port, &pagesize);
(void) host_statistics(host_port, HOST_VM_INFO, (host_info_t)&vm_stat, &host_size);
return vm_stat.free_count * pagesize;
}
-(vm_size_t) usedMemory {
struct task_basic_info info;
mach_msg_type_number_t size = sizeof(info);
kern_return_t kerr = task_info(mach_task_self(), TASK_BASIC_INFO, (task_info_t)&info, &size);
return (kerr == KERN_SUCCESS) ? info.resident_size : 0; // size in bytes
}
-(void) captureMemUsage {
prevMemUsage = curMemUsage;
curMemUsage = [self usedMemory];
memUsageDiff = curMemUsage - prevMemUsage;
curFreeMem = [self freeMemory];
}
-(NSString*) captureMemUsageGetString{
return [self captureMemUsageGetString: @"Memory used %7.1f (%+5.0f), free %7.1f kb"];
}
-(NSString*) captureMemUsageGetString:(NSString*) formatstring {
[self captureMemUsage];
return [NSString stringWithFormat:formatstring,curMemUsage/1000.0f, memUsageDiff/1000.0f, curFreeMem/1000.0f];
}
@end
Ответ 7
Похоже, вы могли бы использовать хорошо обработанную библиотеку для задачи получения веб-изображений. У Nimbus есть класс сетевого изображения, который делает это эффективно.