菜鳥教程——iOS動態庫與靜態庫

weixin_33912445發表於2017-07-05

一.簡介

庫是程式設計中常用的資料包,更加方便的共享程式碼,提高開發效率,增加程式健壯性和安全性,iOS中的庫可以分為動態庫和靜態庫,兩者的區別就是靜態庫在編譯時把二進位制檔案完整的拷貝的可執行檔案中,多次使用會造成冗餘,這無疑加重了程式的負荷。而動態庫則不同,在編譯的時候並不進行拷貝,而是在執行的時候系統動態載入到記憶體,也只會載入一次,節省記憶體,蘋果是不支援開發者自行建立動態庫並用於釋出,這樣的專案是不會通過appleStore稽核的,雖然iOS8蘋果開放了api介面支援動態載入動態庫。

二.動態庫和靜態庫格式區別

動態庫: .dylib(現在一般為.tdb)和 .framework

靜態庫: .a和 .framework

三.建立動態庫和靜態庫的注意事項

1.架構

armv6|armv7|armv7s|arm64都是ARM處理器的指令集,這些指令集都是向下相容的,例如armv7指令集相容armv6,只是使用armv6的時候無法發揮出其效能,無法使用armv7的新特性,從而會導致程式執行效率沒那麼高。

還有兩個我們也很熟悉的指令集:i386|x86_64 是Mac處理器的指令集,i386是針對intel通用微處理器32架構的。x86_64是針對x86架構的64位處理器。所以當使用iOS模擬器的時候會遇到i386|x86_64,iOS模擬器沒有arm指令集。

模擬器:

iPhone4s-iPnone5:i386

iPhone5s-iPhone7 Plus:x86_64

真機:

arm64:iPhone5S| iPad Air| iPad mini2(iPad mini with Retina Display)

armv7s:iPhone5|iPhone5C|iPad4(iPad with Retina Display)

armv7:iPhone3GS|iPhone4|iPhone4S|iPad|iPad2|iPad3(The New iPad)|iPad mini|iPod Touch 3G|iPod Touch4

armv6 裝置: iPhone, iPhone2, iPhone3G, 第一代、第二代 iPod Touch(一般不需要去支援)

四.建立動態庫和靜態庫

1  .a靜態庫的製作

a).建立Xcode工程staticTest

5423383-e443285fcf773e1b.png

建立好的工程如圖所示

b)新增方法


5423383-451399414f97999b.png

c)修改配置資訊

我們需要把Build Active Architecture Only修改為NO,否則生成的靜態庫就只支援當前選擇裝置的架構。


5423383-3f8b1518dab832db.png

(1)Architectures

Space-separated list of identifiers. Specifies the architectures (ABIs, processor models) to which the binary is targeted. When this build setting specifies more than one architecture, the generated binary may contain object code for each of the specified architectures.

指定工程被編譯成可支援哪些指令集型別,而支援的指令集越多,就會編譯出包含多個指令集程式碼的資料包,對應生成二進位制包就越大,也就是ipa包會變大。

(2)Valid Architectures

Space-separated list of identifiers. Specifies the architectures for which the binary may be built. During the build, this list is intersected with the value of ARCHS build setting; the resulting list specifies the architectures the binary can run on. If the resulting architecture list is empty, the target generates no binary.

限制可能被支援的指令集的範圍,也就是Xcode編譯出來的二進位制包型別最終從這些型別產生,而編譯出哪種指令集的包,將由Architectures與Valid Architectures(因此這個不能為空)的交集來確定,例如:

比如,你的Valid Architectures設定的支援arm指令集版本有:armv7/armv7s/arm64,對應的Architectures設定的支援arm指令集版本有:armv7s,這時Xcode只會生成一個armv7s指令集的二進位制包。

再比如:將Architectures支援arm指令集設定為:armv7,armv7s,對應的Valid Architectures的支援的指令集設定為:armv7s,arm64,那麼此時,XCode生成二進位制包所支援的指令集只有armv7s。


5423383-9c3d9ab7acd89ee5.png
5423383-242b98f9f4ce78fd.png

d).分別在Generic ios device 和真機,模擬器上編譯程式,可以看到product檔案由紅邊黑,右鍵找到檔案。

5423383-da33877627e6e43d.png
5423383-ac0eb073e8dc9908.png

可以看到模擬器和真機生成的.a 檔案。

e).將兩個.a檔案合併成一個.a檔案,同時支援模擬器和真機。

我們可以使用終端命令來實現。命令格式:lipo -create 第一個.a檔案的絕對路徑 第二個.a檔案的絕對路徑 -output 最終的.a檔案路徑:

然後我們可以呼叫.h和.a檔案執行到真機和模擬器上。

2  .framework靜態庫的製作

a).建立framework檔案,建立後如圖:

5423383-31d3e565268d6997.png

b).建立類並定義方法。

5423383-7bcb7ff5d2c54138.png

c).按照前面說的做相關配置,另外需要把自己用到的類從project拖拽到public裡。

5423383-6e5ba5122b1f9448.png

d).將Mach-O Type改為靜態,這個預設是dynamic

5423383-603933d7b5a30188.png

e).分別編譯,可以看到.frameWork邊黑

5423383-994bdf26e0fe3cc8.png

f).右鍵開啟,如圖

5423383-fc4b34b432b33546.png

g).將每個Framework檔案下包含的testFrameWork二進位制檔案,合併生成同時支援真機和模擬器的檔案包,

 終端操作:lipo -create 第一個framework下二進位制檔案的絕對路徑 第二個framework下二進位制檔案的絕對路徑 -output  最終的二進位制檔案路徑: 

5423383-8d953b5063b103d1.png

h).此刻已經完成庫建立,使用的時候將生成的test二進位制檔案替換原真機或模擬器資料夾中生成的二進位制檔案即可。

注意:

如果靜態庫中有category類,則在使用靜態庫的專案配置中Other Linker Flags需要新增引數-ObjC或者-all_load。

如果建立的framework類中使用了.tbd,則需要在實際專案中匯入.tbd動態庫。

相關文章