OC的动态性
OC是一门动态的语言,这门语言的动态性变现在哪些方面呢?
1.动态类型
程序分为编译时和运行时,编译时将程序转换成机器可以理解的语言,在这一过程中对语言进行最基本的检查报错,包括语法和类型等,但是编译成功并不代表程序可以成功运行。编译是一个静态的阶段。
运行时:运行时是将程序编译好的代码装载进内存开始运行的阶段,在这一阶段会对程序的类型和方法进行具体的检查,此时若出错程序会奔溃。运行时是一个动态的阶段。
动态类型是指将程序的类型推迟到运行时才起决定,比如id类型,这个类型会在运行时根据赋给它的指针来确定它真实的类型,或者根据isKindOfClass来判断程序的类型。其他在程序编写时定义的类型如NSString则是在编译阶段就被确定的类型。所以说id是一个动态的类型,而其他则是静态的类型。
下面看一段代码:
NSString *str = [NSData data];
这段代码我们command+B编译发现程序可以运行通过,但是Xcode会进行警告,因为指针指向的类型为NSString,
但是赋值为NSDate对象,所以在编译时会警告,但是编译时其类型依然作为NSString类型来编译
NSString *str = [NSData data];
[str stringByAppendingString:@"字符串"];
在这里进行编译发现编译也可以通过,因为str在编译时的类型为NSString,所以它调用字符串的方法是可以编译
通过的,但是我们运行程序发现此时程序会崩溃,此时我们打一个断点来看一下str在运行时的类型
屏幕快照 2017-06-29 11.19.38.png
此时我们可以看到str在程序运行时的类型为NSData,这就是OC的动态类型,将程序的真实类型推迟到程序运行时才去决定。
OC在运行时的类型的判断是用内省来判断的,在运行时程序内部调用了class、NSClassFromString、NSStringFromClass、isKindOfClass、isMemberOfClass、respondsTosSelector、instancesRespondToSelector等一堆方法结合判断对象真实类型以及是否有这个方法。
动态绑定
动态绑定主要是指利用OC的消息传递机制,将要执行的方法的确定推迟到运行时,可以动态添加方法。动态绑定的核心就是运行时为类添加属性和方法,以及方法的处理和转发。这点其实就是OC的消息处理的三步以及运行时为对象添加属性(objc_setAssociatedObject)
动态加载
动态加载指的有两方面:1.动态资源的加载 2.部分可执行代码模块的加载,这些资源在程序运行时动态的选择性加载。动态资源的加载典型就是程序中不同像素的图片的加载,程序会根据当前屏幕的像素来加载。 部分可执行代码模块的加载指的程序中典型的懒加载。