- 使用Xcode自帶的靜態分析工具 Product->Analyze(快捷鍵command+shift+B)可以找出代碼潛在錯誤,如內存泄露,未使用函數和變量等
所謂靜態內存分析, 是指在程序沒運行的時候, 通過工具對代碼直接進行分析
根據代碼的上下文的語法結構, 讓編譯器分析內存情況, 檢查是否有內存泄露
Analyze主要分析以下四種問題:
- 1、邏輯錯誤:訪問空指針或未初始化的變量等;
- 2、內存管理錯誤:如內存泄漏等; 比如ARC下,內存管理不包括core foundation
- 3、聲明錯誤:從未使用過的變量;
- 4、Api調用錯誤:未包含使用的庫和框架。
缺點: 靜態內存分析由于是編譯器根據代碼進行的判斷, 做出的判斷不一定會準確, 因此如果遇到提示, 應該去結合代碼上文檢查一下
// 面向用戶的文本應該使用本地化的字符串宏
1.user-facing text should use localized string macro
此為代碼中配置了本地化,面向用戶的應該用字符串宏,而我們直接賦值為漢字,因此,此提示可以忽略.
2.instance variable used while 'self' is not set to the result of '[(super or self) init...]
// 此方法提示錯誤
- (instancetype)initWithType:(FTFFavorateType)type
{
if (self == [super init]) {
_type = type;
}
return self;
}
修改為如下
- (instancetype)initWithType:(FTFFavorateType)type
{
if (self = [super init]) {
_type = type;
}
return self;
}
// 在初始化過程中存儲的“持續時間值”的值永遠不會被讀取
3.Value stored to ‘durationValue’ during its initialization is never read
// 此段代碼提示錯誤
NSMutableArray *datesArray = [[NSMutableArray alloc] init];
datesArray = [_onDemandDictionary objectForKey:key];
這是因為[NSMutableArray alloc] init]
初始化分配了內存,而判斷語句里面[_onDemandDictionary objectForKey:key]
方法也相當于初始化分配了內存,就是把初始化的一個新的可變數組賦值給之前已經初始化過的可變數組,看似沒什么大問題,其實存在一個數據源卻申請了兩塊內存的問題,已經造成了內存泄露。
修改為如下
NSMutableArray *datesArray = nil;
datesArray = [_onDemandDictionary objectForKey:key];
Analyze已經分析出imageRef對象有內存泄漏,這種情況在編譯時是無法發現的。
//截取部分圖像
+(UIImage*)getSubImage:(unsigned long)ulUserHeader
{
UIImage * sourceImage = [UIImage imageNamed:@"header.png"];
CGFloat height = sourceImage.size.height;
CGRect rect = CGRectMake(0 + ulUserHeader*height, 0, height, height);
CGImageRef imageRef = CGImageCreateWithImageInRect([sourceImage CGImage], rect);
UIImage* smallImage = [UIImage imageWithCGImage:imageRef];
//CGImageRelease(imageRef);
return smallImage;
}
Analyze邏輯錯誤監測:
test.png
這種情況在codereview時也較難發現,可以借助Analyze。
如上代碼,當Tag不等于1、2和3的時候,就會出現很問題了。
Analyze還給出了箭頭提示:len is a garbage value。建議在聲明變量時,同時進行初始化。