近來沒什麼新項目做,想學習一些swift開源項目,看了幾個文件感覺有點懵,可能水平還沒達到,等用到具體內容的時候再去仔細看吧。 關於現在的項目,想想單元測試還可以完善一下,就在framwork工程中寫了一些測試用例。準備開始測試之前,先用product-analyze(快捷鍵cmd+shift+b) ...
近來沒什麼新項目做,想學習一些swift開源項目,看了幾個文件感覺有點懵,可能水平還沒達到,等用到具體內容的時候再去仔細看吧。
關於現在的項目,想想單元測試還可以完善一下,就在framwork工程中寫了一些測試用例。準備開始測試之前,先用product-analyze(快捷鍵cmd+shift+b)分析一下,發現有未釋放的對象。
CFUUIDRef uuidRef = CFUUIDCreate(kCFAllocatorDefault); NSString *strUUID = (NSString *)CFBridgingRelease(CFUUIDCreateString(kCFAllocatorDefault,uuidRef)); NSData *deviceid = [strUUID dataUsingEncoding:NSUTF8StringEncoding]; CFRelease(uuidRef);//Potential leak of an object stored into 'uuidRef'
原來是在創建uuid的方法中,沒有釋放uuidRef這個cf對象,最後加上CFRelease就可以了。
但是在上面的第二行代碼中,有CFBridgingRelease方法,表示把cf對象轉換為oc對象,包括所有權轉換,之後可以由arc自動釋放對象。
再仔細看過後,發現原來上面的代碼中其實有兩個cf對象,把第二行中拆分成下麵這樣,其中__bridge可以把cf對象轉為oc對象,不包括所有權轉換,所以最後面有CFRelease釋放stringRef對象。
再次運行analyze,又報其它錯誤
CFUUIDRef uuidRef = CFUUIDCreate(kCFAllocatorDefault); CFStringRef stringRef = CFUUIDCreateString(kCFAllocatorDefault,uuidRef); NSString *uuid = (__bridge NSString *)stringRef; NSData *deviceId = [uuid dataUsingEncoding:NSUTF8StringEncoding]; CFRelease(uuidRef);//Potential leak of an object stored into 'uuidRef' CFRelease(stringRef);//Reference-counted object is used after it is released
對象釋放之後仍然有使用,創建對象,使用完畢後釋放對象,很對的,難道什麼地方寫得不對嗎?
在stackoverflow上找到類似的問題及解決方法,比較之後發現是需要重新拷貝一份uuid對象,因為在調用CFRelease之後,之前的uuid會被釋放掉,再把之前的uuid作為函數返回值返回時,就會報錯。
最後正確的寫法改為
//(NSString *)CFBridgingRelease(stringRef) 相當於__bridge__transfer把cf對象轉成oc對象,所有權也由cf轉到oc,arc下會自動釋放 //__bridge 只是把cf對象轉為oc,不包含所有權的轉換 //CFBridgingRetain(id) 相當於__bridge__retained把oc對象轉為cf對象,所有權也由oc轉到cf,需要手動釋放 CFUUIDRef uuidRef = CFUUIDCreate(kCFAllocatorDefault); CFStringRef stringRef = CFUUIDCreateString(kCFAllocatorDefault,uuidRef); NSString *uuid = [NSString stringWithString:(__bridge NSString *)stringRef]; NSData *deviceId = [uuid dataUsingEncoding:NSUTF8StringEncoding]; CFRelease(uuidRef);//Potential leak of an object stored into 'uuidRef' CFRelease(stringRef);//Reference-counted object is used after it is released
看左側的博客目錄發現三月份竟然一篇都沒有寫,上個月是有點荒廢了,事情有點多。之後儘量保持每月至少一篇技術博客,多學習一些東西,找到值得記錄的內容。加油吧!