問(wèn)題:
- iOS開(kāi)發(fā)中我們經(jīng)常會(huì)遇到這種錯(cuò)誤
Undefined symbols for architecture arm64
這個(gè)錯(cuò)誤表示工程某些地方不支持arm64指令集沛硅。而這個(gè)問(wèn)題基本上是由于引入了他人的靜態(tài)庫(kù)。
問(wèn)題分析:
- 對(duì)于iOS設(shè)備來(lái)說(shuō)iOS的指令集有
armv6偏化、armv7洪囤、armv7s缚去、arm64
這樣四種雕凹,不同型號(hào)的iOS設(shè)備使用不同的指令集,下面是各自的區(qū)別:
armv6
- iPhone汽抚、iPhone 3G
- iPod 1G抓狭、iPod 2G
armv7
- iPhone 3GS、iPhone 4
- iPod 3G造烁、iPod 4G否过、iPod 5G
- iPad、iPad 2惭蟋、iPad 3苗桂、iPad Mini
armv7s
- iPhone 5、iPhone 5C
- iPad 4
arm64
- iPhone 5S iPhone 6 iPhone 6Plus
- iPad Air, Retina iPad Mini
問(wèn)題解決:
1.檢查一下靜態(tài)庫(kù)的配置路徑是否正確
Build Settings>Search Paths>Library Search Path
(一定要認(rèn)真檢查)
2.查看了靜態(tài)庫(kù)所支持的架構(gòu)
打開(kāi)終端輸入查看命令lipo - info xxx.a ,結(jié)果如下:
3.檢查一下Architectures的配置
Architectures:該編譯選項(xiàng)指定了工程將被編譯成支持哪些指令集告组,支持指令集是通過(guò)編譯生成對(duì)應(yīng)的二進(jìn)制數(shù)據(jù)包實(shí)現(xiàn)的誉察,如果支持的指令集數(shù)目有多個(gè),就會(huì)編譯出包含多個(gè)指令集代碼的數(shù)據(jù)包惹谐,造成最終編譯的包很大。
Build Active Architectures Only:當(dāng)該選項(xiàng)設(shè)置成YES時(shí)驼卖,你連上一個(gè)armv7指令集的設(shè)備氨肌,就算你的Valid Architectures和Architectures都設(shè)置成armv7/armv7s/arm64,還是依然只會(huì)生成一個(gè)armv7指令集的二進(jìn)制包酌畜。通常情況下怎囚,該編譯選項(xiàng)在Debug模式都設(shè)成YES,Release模式都設(shè)成NO桥胞。
Valid Architectures:該編譯項(xiàng)指定可能支持的指令集恳守,該列表和Architectures列表的交集,將是Xcode最終生成二進(jìn)制包所支持的指令集贩虾。
注意:1催烘、指令集是向下兼容的。比如缎罢,armv7s指令集的設(shè)備伊群,可以兼容運(yùn)行使用armv7考杉、armv6編譯的程序〗⑹迹可以根據(jù)自己需要配置崇棠。
4.設(shè)置編譯參數(shù)
Build Settings -> Linking -> Other Linker Flags
添加對(duì)應(yīng)的庫(kù)文件:-lAPayLib
注:
1.前面加橫杠’-‘,l,編譯的時(shí)候xcode默認(rèn)會(huì)自動(dòng)把庫(kù)名加上lib前綴。
2.如果靜態(tài)庫(kù)有category,那么需要添加-ObjC參數(shù)標(biāo)識(shí)丸卷,否則可能會(huì)報(bào):unrecognized selector sent to instance
3.參數(shù)說(shuō)明引用
- -ObjC:加了這個(gè)參數(shù)后枕稀,鏈接器就會(huì)把靜態(tài)庫(kù)中所有的Objective-C類和分類都加載到最后的可執(zhí)行文件中
- -all_load:會(huì)讓鏈接器把所有找到的目標(biāo)文件都加載到可執(zhí)行文件中,但是千萬(wàn)不要隨便使用這個(gè)參數(shù)谜嫉!假如你使用了不止一個(gè)靜態(tài)庫(kù)文件萎坷,然后又使用了這個(gè)參數(shù),那么你很有可能會(huì)遇到ld: duplicate symbol錯(cuò)誤骄恶,因?yàn)椴煌膸?kù)文件里面可能會(huì)有相同的目標(biāo)文件食铐,所以建議在遇到-ObjC失效的情況下使用-force_load參數(shù)。
- -force_load:所做的事情跟-all_load其實(shí)是一樣的僧鲁,但是-force_load需要指定要進(jìn)行全部加載的庫(kù)文件的路徑虐呻,這樣的話,你就只是完全加載了一個(gè)庫(kù)文件寞秃,不影響其余庫(kù)文件的按需加載
4.編譯方式引用
靜態(tài)庫(kù)中采用ObjectC++實(shí)現(xiàn)斟叼,因此需要您保證您工程中至少有一個(gè).mm后綴的源文件(您可以將任意一個(gè).m后綴的文件改名為.mm),或者在工程屬性中指定編譯方式春寿,即將XCode的Project -> Edit Active Target -> Build -> GCC4.2 - Language -> Compile Sources As設(shè)置為"Objective-C++"