眾所周知,在App Store中超過一定大小的文件只能使用WiFi下載(近期提升到了150M,之前是100M)。雖然提升了一點,但是我們仍需要注意安裝包的大小。畢竟除了游戲很少有人喜歡下很大的應用。
那么如何知道是哪些文件占得空間比較大呢?有一個比較簡單的方法就是找到IPA包,解壓得到.app文件,顯示包內容,就可以查看到里面的東西了。
*注意:.app bundle是經過壓縮的,並且有些文件的壓縮效果要比別的文件好,所以壓縮后的效果才是才是最重要的。不過一般情況下在壓縮前最大的文件,在壓縮后依舊是最大的文件。我們可以將某個文件刪除,然后在Finder中右鍵單擊,選擇壓縮,這樣可以更加精確的測量文件壓縮效果。
bundle如果你不懂的話可以查看這篇文章。參考
看到這里我們就知道一個ipa里面大文件都有哪些了,然后就可以針對性的修改。
說了上面一些,下面開始說一些干貨吧。
首先是Xcode編譯選項優化。經過下面這些設置,你的APP就會小很多。
Xcode編譯選項優化方法:
1.舍棄架構armv7
armv7用於支持4s和4,4s是2011年11月正式上線,雖然還有小部分人在使用,但是追求包體大小的完全可以舍棄了。
2.冗余代碼剝離
build setting 里 DEAD_CODE_STRIPPING = YES(好像默認就是YES)。 確定 dead code(代碼被定義但從未被調用)被剝離,去掉冗余的代碼,即使一點冗余代碼,編譯后體積也是很可觀的。

3.編譯器優化級別
Build Settings->Optimization Level有幾個編譯優化選項,release版應該選擇Fastest, Smalllest[-Os],這個選項會開啟那些不增加代碼大小的全部優化,並讓可執行文件盡可能小。
4.配置編譯選項
(Levels選項內)Generate Debug Symbols 設置為NO,這個配置選項應該會讓你減去小半的體積。注意這個如果設置成NO就不會在斷點處停下
5.去除符號信息
Strip Debug Symbols During Copy 和 Symbols Hidden by Default 在release版本應該設為yes,可以去除不必要的調試符號。Symbols Hidden by Default會把所有符號都定義成”private extern”,設了后會減小體積。
6.Strip Linked Product:DEBUG下設為NO,RELEASE下設為YES,用於RELEASE模式下縮減app的大小;
7.編譯器優化,去掉異常支持。Enable C++ Exceptions、Enable Objective-C Exceptions設置為NO,Other C Flags添加-fno-exceptions
接下來就是資源文件了,這些都是占大頭的。
在開發中我們會使用一些本地圖片,本地資源,三方SDK之類的。這些東西會占用很大的內存。下面我會一一解決。
1.本地資源文件
一些大圖片或者音視頻我們不會設置成網絡,而是存儲在本地,這就導致的IPA包的加大。
精簡本地資源文件方法:
(1)壓縮資源文件,如使用 ImageOptim 或者 TinyPng 來壓縮圖片,還可以在調整一下音視頻的碼率,減小體積;
(2)把一些資源放在網絡上,如一些非第一時間加載需要的資源文件(需要根據不同業務邏輯進行判斷)放置在網絡上,在加載完成后靜默下載存儲在本地。留存之后使用。
(3)簡單的圖片可以使用代碼自動生成。很類似的圖片,僅僅只有顏色不同,可以通過代碼處理圖片的顏色。
(4)Xcode 中也會有一些圖片相關設置,Compress PNG Files 和 Remove Text Medadata From PNG Files。前者打包的時候自動對圖片進行無損壓縮,后者會移除 PNG 圖像名稱、作者、版權、創作時間、注釋等信息。
1 -(UIImage*)imageChangeColor:(UIColor*)color{ 2 UIGraphicsBeginImageContextWithOptions(self.size, NO, 0.0f);//獲取畫布 3 [color setFill];//畫筆沾取顏色 4 CGRect bounds = CGRectMake(0, 0, self.size.width, self.size.height); 5 UIRectFill(bounds); 6 [self drawInRect:bounds blendMode:kCGBlendModeOverlay alpha:1.0f];//繪制一次 7 [self drawInRect:bounds blendMode:kCGBlendModeDestinationIn alpha:1.0f];//再繪制一次 8 UIImage *img = UIGraphicsGetImageFromCurrentImageContext(); 9 UIGraphicsEndImageContext();//獲取圖片 10 return img; 11 } 12 13 + (UIImage *)getLaunchImage{ 14 CGSize viewSize = [UIScreen mainScreen].bounds.size; 15 NSString *viewOr = @"Portrait";//垂直 16 NSString *launchImage = nil; 17 NSArray *launchImages = [[[NSBundle mainBundle] infoDictionary] valueForKey:@"UILaunchImages"]; 18 for (NSDictionary *dict in launchImages) { 19 CGSize imageSize = CGSizeFromString(dict[@"UILaunchImageSize"]); 20 if (CGSizeEqualToSize(viewSize, imageSize) && [viewOr isEqualToString:dict[@"UILaunchImageOrientation"]]) { 21 launchImage = dict[@"UILaunchImageName"]; 22 } 23 } 24 return [UIImage imageNamed:launchImage]; 25 }
補充:
音頻的壓縮參考WWDC中的Audio Development for Games,里面介紹了如何有效的處理音頻。常規來說,我們要使用AAC或MP3來壓縮音頻,並且可以嘗試降低一下音頻的比特率。有時候44.1khz的采樣是沒有必要的,稍微低一點的比特率也不會降低音頻的質量。
圖片方面盡量使用8-bit圖片(使用8-bit的PNG圖片會比32-bit的圖片能減少4倍的壓縮率。但是8-bit的圖片支持最多256種不同的顏色,所以8-bit的圖片一般只應該用於一小部分的顏色圖片。例如灰度圖片最好使用8-bit。)針對32-bitt的圖片盡量使用高壓縮的比率:利用Adobe Photoshop的Save For Web可以減小JPEG和PNG的圖片大小。在Xcode中,默認情況下,會自動的使用pngcrush來壓縮.png圖片。
2.Assets.xcassets里的圖片
在版本迭代中我們也會遇到一下界面調整,圖片更換的情況,尤其是在一些活動或者主題色變化時,經常會往里面添加新圖片,一些老圖片可能就不會刪除,久而久之,圖片大小就越來越大。
精簡圖片的方法:
(1)使用在線壓縮png圖片網站來壓縮圖片:compresspng或tinypng
(2)一些比較大體積的背景圖片壓縮成.jpg格式的。
(3)刪除無用圖片
用LSUnusedResource這個軟件查找項目中沒有用到的圖片,然后刪除,當然不一定特別准確,有一些[UIImage imageNamed:[NSString stringWithFormat:@"icon_%d",index]]這樣使用的圖片也會被列在未使用圖片中。
也可以使用這個腳本工具可以大范圍檢測程序中沒有用到的圖片http://blog.csdn.net/songhongri/article/details/21833069
使用方法:1.將.sh文件放到所檢測工程的目錄下,
2.cd到該目錄下,
3.執行腳本:sh unusedImage.sh
注意:這里在刪除未應用的圖片時注意第三方庫里的不能刪除,保險起見相同文件夾下的最好在工程里手動再搜索一次,確定沒有使用到,就可以刪除了。
3.SDK
我之前開發中遇到的一個APP,內容較多功能比較復雜,SDK就有將近200m,雖然知道App Store會有壓縮,可是還是很大,這是我們就需要精簡SDK了。
精簡SDK方法:
(1)最基本的就是去除無用的SDK
(2)盡量使用同一個公司下的SDK,我之前就見過一個開發分享用shareSDK,統計用的友盟,bug分析用的buggly。還有其他的SDK,基本就是一個功能用一套,這不就是很大的問題嗎?在國內公司基本上都是往全的方向做,一個完整的SDK基本上就能包含大部分功能了,所以使用同一個公司的內容,缺失再補充SDK就是一個很好的方法
(3)在使用SDK的時候,我們不需要下載全部的功能,我們可以選擇性下載功能,用不到的功能我們不需要下載。
4.代碼
代碼方面也有很多需要注意的地方,如一些readme文件和一些迭代中產生的無效代碼等。
精簡代碼的方法:
(1)將數據從代碼中剝離出來
將所有的資源(例如很長的字符串)從代碼中剝離出來,並存入外部文件,這樣會減小最終文件下載的大小,因為這些文件的壓縮效果更好。(參考iOS App Store Specific Considerations中的完整介紹。)
(2)無用代碼的刪除
通過 AppCode 打開對應的工程文件 選擇 Code -> inspect Code 分析代碼,去掉無用的引用及代碼。查找內部使用到的第三方庫,一方面可以進行刪減代碼,用不到的類,可以直接刪除,還有把第三方庫中的圖片資源刪除掉。
(3)一些文檔的替換
在開發中我們可能會有一些文檔之類的在代碼中,但是在迭代后可能會沒有用,我們可以刪除這些東西來減小體積。