什么是库?
库就是程序代码的集合, 将N个文件组织起来, 是共享程序代码的一种方式
库的分类?
开源库: 源码是公开的, 可以看到每个实现文件 .m 的实现, 例如 Github 上常用的开源库 AFNetworking, SDWebImage 等.
闭源库: 不公开源码, 是经过编译后的二进制文件, 看不到具体的实现. 闭源库又分为: 静态库 和 动态库
静态库的存在形式?
.a
.framework
动态库的存在形式?
.dylib
.framework
静态库和动态库的区别?
.a 文件肯定是静态库, .dylib 肯定是动态库, .framework 可能是静态库也可能是动态库
静态库在链接时, 会被完整的赋值到可执行文件中, 如果多个APP都使用了同一个静态库, 那么每个APP都会拷贝一份, 缺点是浪费内存, 类似于定义一个基本变量, 使用该基本变量是新复制了一份数据, 而不是原来定义的
动态库不会复制,只有一份, 程序运行时动态加载到内存中, 系统只会加载一次, 多个程序公用一份, 节约了内存. 类似于使用变量的内存地址一样. 使用的是同一个变量
但是项目中如果使用了自己定义的动态库, 苹果是不允许上架的, 在 iOS8 后 苹果开放了动态加载 .dylib 的接口, 用于挂载 .dylib 动态库
静态库的运用场景?
保护自己的核心代码, 如讯飞语音摸索了好多年探索出的结果当然要保存起来, 都公开了公司怎么生存
将MRC的项目打包成静态库, 可以在ARC下直接使用, 不用转换, 如别人使用 MRC 写的开源库, 放到自己的ARC项目中, 需要对每个文件加一个编译参数-fno-objc-arc这样相对来说很麻烦, 将整个工程打包成静态库直接放到项目中即可, 也不用对每个文件添加编译选项
静态库的特点?
.a + .h
.a : 可以看做所有 .m 文件加密后的一个二进制文件
.h : 头文件, 用户暴露可用的接口 (方法)
制作静态库的过程 .a
new -> project -> Cocoa Touch Static Liabrary
编写逻辑代码
Build Phases -> Copy Files 添加要暴露的头文件
Build Setting -> Build Active Architecture only (只构建活跃构架) -> nO
a. 所有模拟器调试版本静态库: 选中模拟器 command + b
b. 真机调试版本静态库: 选中 generic iOS Device , Command + b
c. 真机发布静态库: 选中 generic iOS Device , Edit scheme Run -> Build Configuration -> Release. command +b
工程文件夹 Produts 下的 .a 文件就是编译得到的静态文件
右键 show finder 查看所有版本的静态库
Debug-iphonesos 调试 真机版本
Debug-iphonesimulator 调试 模拟器版本
Release-iphoneos 发布 真几版本
Release-iphonesimulator 发布 模拟器版本
8 . 如何引入静态库?
直接把 对应静态库 .a 和 暴露的.h 文件 拖入到 目标工程中即可
合并静态库?
lipo -create 模拟器调试.a 模拟器发布.a 真机调试.a 真机发布.a output 通用.a
静态库注意:
自己的静态库给别人用, 一般都是给两个发布版本 (模拟器, 真机), 最好不要合并. 如果给了用户合并版的, 用户无法分解.
关于 lipo 命令
关于构架:
构架是什么?
CPU 构架 是 CPU 厂商给属于同一系列的 CPU 产品定的一个规范, 主要目的是为了区分不同类型 CPU 的重要指示, 模拟器上的构架和真机上的构架不是一样的, 模拟器和模拟器之间, 真机和真机之间的构架也是不同的, 如果静态库的构架和测试项目对应的模拟器或者真机上的构架不对应就会报错 "Undefined symbols for architecture arm64/i386"
查看静态库对应的构架: lipo -info Xxx.a
静态库都支持哪些构架?
模拟器架构
iPhone4s ~ 5 : i386
iPhone5s ~ 7Plus : x86_64
真机架构
3GS~4s : armv7
5/5c : armv7s(armv7兼容armv7s)
5s ~ 6sPlus : arm64
模拟器32位处理器测试需要i386架构,
模拟器64位处理器测试需要x86_64架构,
真机32位处理器需要armv7,或者armv7s架构,
真机64位处理器需要arm64架构。
静态库的制造过程 .framework
new -> project -> Cocoa Touch Framework
Build Settings -> Mach-O Type -> Static Library (默认是 Dynamic Library)
编写逻辑代码
公开头文件 Build Phases -> Headers -> 把Project 中需要暴露的 .h 文件拖到 Public 中
将要公开的所有头文件 引入到 总的头文件 (库名.h) 中,
Build Setting -> Build Active Architecture Only -> NO
同 静态库.a 制作的步骤 5
项目文件夹 Products 下 的 库名.framework 右键 show finder
同 .a 静态库制作的步骤7 得到所有类型版本的framework
将 需要的framework 拖入到目标工程中, 调用静态库的方法
2.动态库 .framework
步骤跟 静态库 .framework 类似, 下面是不同的地方
1. Mach-O type -> Dynamic Library
将生成的动态库 .framework 拖入到目标工程之后
2. General -> Embedded Binaries 中 添加该.framework
3. Linked Frameworks and libraries 中 会默认添加该 .framework
swift framework 动态库 (swift 不支持静态库)
1. File --> project --> Cocoa Touch Framework (选择swift 语言)
创建你需要的 swift 文件. 完成代码逻辑
2. Build Phases --> Headers Public 中添加所有用得到的swift 文件
要注意: 所有要暴露出来的swift 类和方法 都必须用public 修饰
3. Build Settings -> Mach-O type 选择 Dynamic library (swift 语言智能选择动态库)
4. Build Active Architecture Only 设为 NO
5. command + b 编译一遍代码, 如果没有问题的话, 动态库已经生成好了
6. 工程文件夹 Products文件夹中 有个.framework 文件, 选中, 右键 show finder
7. 可以拿到 .framework 文件
8. 把 framework 文件拖入要用到的工程中
9. General --> Embedded Binaries 中加入刚刚拖进去的 framework
10. 当framework 拖入工程后 xcode 会自动给 swift类型的 framework 创建一个文件 (库名-swift.h)
11. 工程中 引入 文件 库名-swift.h 后, 就可以调用所有 framework中暴露出来的 swift 方法.
有时候项目需要在集成C++静态库的基础之上,去用OC进行封装暴露对外的接口,实现iOS中SDK的完成。
在C++编译静态库的过程中,有个bitcode选项要注意,用C++编译静态库的时候,尽量支持bitcode否则,你在链接的时候会出现错误。你需要设置工程中target的Enable Bitcode为NO才可以正常编译。
在程序支持的编译框架中可以在Architectures中选择arm64 /arm64e/armv7...
Xcode设置项之Architectures和Valid Architectures和Build Active Architectures Only参数的选择 应当特别注意
项目中编译c++文件的时候,需要修改项目中任意一个.m文件的后缀为.mm否则编译不通过
项目中的资源文件应该放在bundle文件中,利用oc中的从bundle文件中取资源的方式存取。