函数派发

Swift中函数的派发机制有三种:静态派发,函数表派发,消息派发。

静态派发

静态派发是指在运行时不需要查表,直接跳转到方法进行执行。静态派发的性能也是最高的。c语言采用的是直接派发。

函数表派发

class类型采用函数表派发。当一个对象调用一个函数时,会从对象的头8字节找到该对象的元信息。从元信息的函数表中找到执行的函数地址,并执行函数。

对象的元信息会在编译时写入macho文件中。

class Animal {
func speak() {
print("Animal speak")
}
func eat() {
print("Animal eat")
}
func sleep() {
print("Animal sleep")
}
}
class Dog: Animal {
override func speak() {
print("Dog speak")
}
override func eat() {
print("Dog eat")
}
func run() {
print("Dog run")
}
}class Animal {
func speak() {
print("Animal speak")
}
func eat() {
print("Animal eat")
}
func sleep() {
print("Animal sleep")
}
}
class Dog: Animal {
override func speak() {
print("Dog speak")
}
override func eat() {
print("Dog eat")
}
func run() {
print("Dog run")
}
}

Dog继承于Animal。let dog: Dog = Dog()dog 变量指向Dog对象。Dog对象在堆内存中。Dog对象的前8字节存有Dog对象的元信息。Dog对象的元信息中有该类的函数指针表。Dog中override父类Animal的函数会替换掉父类的函数存于Dogd的函数指针中。

### 消息派发

继承于NSObject的采用的是消息派发。Swift可以通过dynamic修饰来支持消息派发机制。

函数派发场景分析

在选择派发方式时,在编译期间就能决定执行哪个函数就采用静态派发。需要在运行期间决定执行哪个函数的就需要用函数表派发或者消息派发。不具动态性的的场景默认采用静态派发,这样派发效率更高。

struct无法继承,也就不具有动态性,函数派发在编译期间就能确定。

class和协议的 extension无法被子类继承,函数派发在编译期间就能确定。

class和协议的初始化方法,因为绝大多数时候需要被override的,所以采用函数表派发。

class的其他方法,如果没有被override,一般是函数表派发,但编译器也可能优化成直接派发。

class的 @objcextension能够继承,函数派发在执行期决定,并且是采用的是消息派发。

不继承NSObject的纯Swift,@objc的extension,采用的消息派发有点迷。消息派发机制需要有Objective-C的运行时,不继承与NSObject能有运行时的信息吗。该类的对象,

class FunctionDispatchObject {
func test1() {
print("test1")
}
}
extension FunctionDispatchObject {
@objc public func test2() {
print("test2")
}
}
// test1采用函数表派发
// test2采用消息机制派发:test2虽然写在extension里,当家里@objc,具有了动态性,可以继承了。class FunctionDispatchObject {
func test1() {
print("test1")
}
}
extension FunctionDispatchObject {
@objc public func test2() {
print("test2")
}
}
// test1采用函数表派发
// test2采用消息机制派发:test2虽然写在extension里,当家里@objc,具有了动态性,可以继承了。

领略一下swift函数派发机制流程的更多相关文章

  1. 深入理解 Swift 派发机制

    原文: Method Dispatch in Swift作者: Brain King译者: kemchenj 译者注: 之前看了很多关于 Swift 派发机制的内容, 但感觉没有一篇能够彻底讲清楚这件 ...

  2. swift派发机制的核心是确定一个函数能否进入动态派发列表

    swift派发机制的核心是确定一个函数能否进入动态派发列表

  3. swift 该死的派发机制--待完成

    swift 该死的派发机制 final static oc类型 多态类型 静态类型 动态函数  静态函数 nsobject: 1.缺省不再使用oc的动态派发机制: 2.可以使用nsobject暴露出来 ...

  4. swift 即使不使用oc的动态派发机制也应该借鉴isa类型识别机制

    目前的消息派发机制真的很鸡肋. 简直是一堆狗屎. 类型信息中包含所有需要动态派发的函数:这个包含两类:类和protocol: 在编译时,首先搜索动态派发列表: 动态派发列表没有,在搜索静态派发列表: ...

  5. Swift的基本类型和流程控制

    Swift  是一门静态的强类型语言.它以简单.干净.可读性好等特点著称. 1. 为什么是静态语言? 首先静态语言比之动态语言,更具有安全性.它不允许类型之间自动的进行转换,必须要显示的转换.Swif ...

  6. [置顶] Android源码分析-点击事件派发机制

    转载请注明出处:http://blog.csdn.net/singwhatiwanna/article/details/17339857 概述 一直想写篇关于Android事件派发机制的文章,却一直没 ...

  7. Swift 静态派发和动态派发

    前言 方法是 Swift 中的一个重要概念,方法允许你把需要复用的代码封装进方法中,这样当你调用方法时,实际上你的想法是执行方法中的那些代码,方法的出现极大的提高了方法的复用性. Swift 工程的环 ...

  8. Android源码分析-点击事件派发机制

    转载请注明出处:http://blog.csdn.net/singwhatiwanna/article/details/17339857 概述 一直想写篇关于Android事件派发机制的文章,却一直没 ...

  9. zookeeper心跳机制流程梳理

    zookeeper心跳机制流程梳理 Processor链Chain protected void setupRequestProcessors() { RequestProcessor finalPr ...

  10. Scala深入浅出实战经典-----002Scala函数定义、流程控制、异常处理入门实战

    002-Scala函数定义.流程控制.异常处理入门实战 Scala函数定义 语句结束无分号 定义无参函数 def 函数名称(参数名称:参数类型)[:Unit=]{ 函数体 } 老师的代码 我的实际代码 ...

随机推荐

  1. Linux用户以及ssh安全相关设置

    Linux用户相关操作 摘要 最近重保, 需要进行网络安全防护. 部分同事处理过程总是顺序有一些不太对的情况. 同时发现自对Linux用户设置也存在很多不清不楚的地方 所以趁着周末学习和总结一下. 用 ...

  2. 随性翻译: Java的运行时参数简单总结

    Java的运行时参数简单总结 简单学习了下Oracle官方的资料: https://docs.oracle.com/javase/8/docs/technotes/tools/unix/java.ht ...

  3. 【K哥爬虫普法】一个人、一年半、挣了2000万!

    我国目前并未出台专门针对网络爬虫技术的法律规范,但在司法实践中,相关判决已屡见不鲜,K 哥特设了"K哥爬虫普法"专栏,本栏目通过对真实案例的分析,旨在提高广大爬虫工程师的法律意识, ...

  4. 【K哥爬虫普法】你很会写爬虫吗?10秒抢票、10秒入狱,了解一下?

    我国目前并未出台专门针对网络爬虫技术的法律规范,但在司法实践中,相关判决已屡见不鲜,K 哥特设了"K哥爬虫普法"专栏,本栏目通过对真实案例的分析,旨在提高广大爬虫工程师的法律意识, ...

  5. webservice--WSDL文件生成本地的代理类

    我们在对应第三方接口时常用:项目上右键---->服务引用---->WCF Web Service,如下图的页面----->填好url后---->转到,就可以发现服务,生成代理类 ...

  6. Fabric网络升级(二)

    原文来自这里. 如果想了解最新版Fabric的特殊事项,详见Upgrading to the latest release of Fabric. 本章只介绍更新Fabric组件的操作.关于如何通过编辑 ...

  7. MyBatis 源码系列:MyBatis 体系结构、六大解析器

    体系结构 MyBatis是一个持久层框架,其体系结构分为三层:基础支持层.核心处理层和接口层. 基础支持层包括数据源模块.事务管理模块.缓存模块.Binding模块.反射模块.类型转换模块.日志模块. ...

  8. git checkout switch restore

    前言 在 Git 术语中,"checkout"是在目标实体的不同版本之间切换的行为.该命令对三个不同的实体进行操作:文件.提交和分支.除了"checkout"的 ...

  9. TienChin 渠道管理-表创建

    在若依当中,有个槽点,就是数据库当中的删除标识状态一般 0 是 false,1 是 true,在若依当中反而 0 是 true,1 是 false. 渠道表设计,我这里就直接贴成品的创建表 SQL: ...

  10. 基于文心大模型套件ERNIEKit实现文本匹配算法,模块化方便应用落地

    文心大模型,产业级知识增强大模型介绍 官网:https://wenxin.baidu.com/ 项目链接见文末 文心大模型开发套件ERNIEKit,面向NLP工程师,提供全流程大模型开发与部署工具集, ...