这是一个自定义view:

@implementation MyView

- (instancetype)init {
if (self = [super init]) {
NSLog(@"调用了init");
}
return self;
} - (instancetype)initWithFrame:(CGRect)frame {
if (self = [super initWithFrame:frame]) {
NSLog(@"调用了initWithFrame");
}
return self;
} @end

现在我调用它的init方法:

MyView *myView = [[MyView alloc] init];

控制台打印信息是:
2017-10-09 11:14:35.224 block[2391:262544] 调用了initWithFrame
2017-10-09 11:14:35.225 block[2391:262544] 调用了init

问:
为什么先打印的是initWithFrame而不是init?

答:

MyView *myView = [[MyView alloc] init];

代码调用过程如下:

  1. 动态查找到 MyView 的 init 方法
  2. 调用 super init 方法
  3. super init 方法内部执行的是 [super initWithFrame:CGRectZero]
  4. 然后 super 会发现 MyView 实现了 initWithFrame 方法
  5. 转而执行 [MyView initWithFrame:CGRectZero]
  6. 最后再执行 init 其余部分

关键点:OC 里面的 super 实际上是让某个类自己去调用父类的方法, 而不是父类去调用某方法。方法动态调用过程中的顺序是按照继承关系从下到上。

或者:

init 内部会调用父类的 initWithFrame: 方法,只不过传入的 frame 的值为0,然后父类的 initWithFrame: 方法发现当前的调用对象是子类对象,所以就调用了子类的initWithFrame方法了。这是一个多态的应用。

Objective-C 【init/initWithFrame调用机制】的更多相关文章

  1. Java方法调用机制

    最近在编程时,修改方法传入对象的对象引用,并没有将修改反映到调用方法中.奇怪为什么结果没有变化,原因是遗忘了Java对象引用和内存分配机制.本文介绍3个点: ① 该问题举例说明 ② 简要阐述Java内 ...

  2. C语言栈调用机制初探

    学习linux离不开c语言,也离不开汇编,二者之间的相互调用在源代码中几乎随处可见.所以必须清楚地理解c语言背后的汇编结果才能更好地读懂linux中相关的代码.否则会有很多疑惑,比如在head.s中会 ...

  3. ectouch第三讲之加载调用机制

    加载与调用机制:         当地址栏键入/mobile,就会加载入口文件index.php:从入口文件里面会调用EcTouch.php公共入口文件,当进入公共入口文件,会定义一些变量,然后加载公 ...

  4. Hadoop之yarn调用机制

    1,Mapper方法:如果在map方法之前执行一些程序用setup,之后用cleanup.同理在Reducer方法中也有setup和cleanup. 2,map任务是并行执行,没有谁先谁后,如果是两个 ...

  5. 8.9.网络编程_Socket 远程调用机制

    1.网络编程 1.1.网络编程概述: 通过通信线路(有线或无线)可以把不同地理位置且相互独立的计算机连同其外部设备连接起来,组成计算机网络.在操作系统.网络管理软件及网络 通信协议的管理和协调下,可以 ...

  6. Scala 基础(九):Scala 函数式编程(一)基础(一)概念、定义、调用机制

    1 概念的说明 1)在scala中,方法和函数几乎可以等同(比如他们的定义.使用.运行机制都一样的),只是函数的使用方式更加的灵活多样. 2)函数式编程是从编程方式(范式)的角度来谈的,可以这样理解: ...

  7. 【学习总结】 init & initWithFrame & initWithCoder

    //当我们所写的程序里没用用Nib文件(XIB)时,用代码控制视图内容,需要调用initWithFrame去初始化 - (id)initWithFrame:(CGRect)frame { if (se ...

  8. init&initWithFrame&initWithCoder

    //当我们所写的程序里没用用Nib文件(XIB)时,用代码控制视图内容,需要调用initWithFrame去初始化 - (id)initWithFrame:(CGRect)frame { if (se ...

  9. Android onTouchEvent, onClick及onLongClick的调用机制

    针对屏幕上的一个View控件,Android如何区分应当触发onTouchEvent,还是onClick,亦或是onLongClick事件? 在Android中,一次用户操作可以被不同的View按次序 ...

随机推荐

  1. GetLastError()返回值列表

    GetLastError()返回值列表: [0]-操作成功完成.[1]-功能错误.[2]-系统找不到指定的文件.[3]-系统找不到指定的路径.[4]-系统无法打开文件.[5]-拒绝访问.[6]-句柄无 ...

  2. oracle查询数据字典的sql

    使用的sql语句如下: select t1.username 用户, t2.TABLE_NAME 表名称, t3.comments 表业务含义, t2.COLUMN_NAME 字段名称, t4.com ...

  3. 《大话设计模式》c++实现 状态模式

    状态模式包含如下角色: Context: 环境类 State: 抽象状态类 ConcreteState: 具体状态类 2)适用场景: a)状态模式主要解决的是当控制一个对象状态转换的条件表达式过于复杂 ...

  4. arm cortex-m0plus源码学习(三)GPIO

    概述: Cortex-m0的integration_kit提供三个GPIO接口,其中GPIO0传输到外部供用户使用,为EXTGPIO:GPIO1是内核自己的信号,不能乱改,会崩掉:GPIO2是一些中断 ...

  5. python pandas简单使用处理csv文件

    这里jira.csv是个大文件 1) >>> import pandas >>> jir=pandas.read_csv(r'C:\Temp\jira.csv') ...

  6. 【转载】unittest参数化(paramunittest)

    前言 paramunittest是unittest实现参数化的一个专门的模块,可以传入多组参数,自动生成多个用例 前面讲数据驱动的时候,用ddt可以解决多组数据传入,自动生成多个测试用例.本篇继续介绍 ...

  7. flask 自定义验证器(行内验证器、全局验证器)

    自定义验证器 在WTForms中,验证器是指在定义字段时传入validators参数列表的可调用对象,下面来看下编写自定义验证器. 行内验证器 除了使用WTForms提供的验证器来验证表单字段,我们还 ...

  8. highchart 柱状图,列宽自适应(x轴是时间的特殊情况)

    1.柱子列宽自适属性: pointWidth:25, //柱子宽度,如果设定该值,则下面2个属性无效 pointPadding: 0.4,//每列之间的距离值,默认此值为0.1 groupPaddin ...

  9. Numpy 基本除法运算和模运算

    基本算术运算符+.-和*隐式关联着通用函数add.subtract和multiply 在数组的除法运算中涉及三个通用函数divide.true_divide和floor_division,以及两个对应 ...

  10. android基本架构

    Android其本质就是在标准的Linux系统上增加了Java虚拟机Dalvik,并在Dalvik虚拟机上搭建了一个JAVA的application framework,所有的应用程序都是基于JAVA ...