viewDidLoad与initWithNibName的调用时机

加载一个ViewController,我们通常使用init或者initWithNibName方法初始化,但是有的时候会出现一些需要初始化的值没有得到正确的设置,下面给出代码看下实际的效果。

第一种情况:正常初始化

FatherViewController:
-(instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if(self){
        NSLog(@"F_init start ");
        self.FPContent = @"F_我是父类初始化的";
        NSLog(@"F_init end");
    }
    return self;
}
- (void)viewDidLoad {
    [super viewDidLoad];
    NSLog(@"F_View");
    NSLog(@"父类的属性值:%@",self.FPContent);
}

SubViewController:
-(instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if(self){
        NSLog(@"S_init start");
        self.FPContent = @"S_我是子类初始化的";
        NSLog(@"S_init end");
    }
    return self;
}
- (void)viewDidLoad {
    [super viewDidLoad];
    NSLog(@"S_View");
    NSLog(@"属性值:%@",self.FPContent);
}

执行结果输出如下:

2018-02-06 16:13:07.236401+0800 YYDemo[70368:2809851] F_init start
2018-02-06 16:13:07.236593+0800 YYDemo[70368:2809851] F_init end
2018-02-06 16:13:07.236878+0800 YYDemo[70368:2809851] S_init start
2018-02-06 16:13:07.236967+0800 YYDemo[70368:2809851] S_init end
2018-02-06 16:13:07.411284+0800 YYDemo[70368:2809851] F_View
2018-02-06 16:13:07.411469+0800 YYDemo[70368:2809851] 父类的属性值:S_我是子类初始化的
2018-02-06 16:13:07.411604+0800 YYDemo[70368:2809851] S_View
2018-02-06 16:13:07.411700+0800 YYDemo[70368:2809851] 属性值:S_我是子类初始化的

第二种情况:在initWithNibName中调用了viewDidLoad

FatherViewController:
-(instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if(self){
        NSLog(@"F_init start ");
        self.FPContent = @"F_我是父类初始化的";
        NSLog(@"F_init end");
    }
    return self;
}
- (void)viewDidLoad {
    [super viewDidLoad];
    NSLog(@"F_View");
    NSLog(@"父类的属性值:%@",self.FPContent);
}

SubViewController:
-(instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if(self){
        NSLog(@"S_init start");
        UILabel *la = [[UILabel alloc] initWithFrame:CGRectMake(88, 20, 100, 20)];
        la.text = self.FPContent;
        [self.view addSubview:la];
        self.FPContent = @"S_我是子类初始化的";
        NSLog(@"S_init end");
    }
    return self;
}
- (void)viewDidLoad {
    [super viewDidLoad];
    NSLog(@"S_View");
    NSLog(@"属性值:%@",self.FPContent);
}    

执行结果输出如下:

2018-02-06 16:19:37.594282+0800 YYDemo[71147:2825509] F_init start
2018-02-06 16:19:37.594492+0800 YYDemo[71147:2825509] F_init end
2018-02-06 16:19:37.594592+0800 YYDemo[71147:2825509] S_init start
2018-02-06 16:19:37.718493+0800 YYDemo[71147:2825509] F_View
2018-02-06 16:19:37.718672+0800 YYDemo[71147:2825509] 父类的属性值:F_我是父类初始化的
2018-02-06 16:19:37.718773+0800 YYDemo[71147:2825509] S_View
2018-02-06 16:19:37.718869+0800 YYDemo[71147:2825509] 属性值:F_我是父类初始化的
2018-02-06 16:19:37.719246+0800 YYDemo[71147:2825509] S_init end

由以上执行结果可知:

在初始化方法总调用View属性的时候就会调用viewDidLoad方法。

viewDidLoad方法一般在视图树构建完成以后调用一次,但是如果VC的View属性被引用,View为nil 的时候也会调用viewDidLoad方法,提前调动该方法可能就会导致某些值不能得到正确的初始化。

原文地址:https://www.cnblogs.com/yinyanlyy/p/8422971.html

时间: 2024-09-30 03:32:01

viewDidLoad与initWithNibName的调用时机的相关文章

MFC浅析(7) CWnd类虚函数的调用时机、缺省实现

CWnd类虚函数的调用时机.缺省实现 FMD(http://www.fmdstudio.net) 1. Create 2. PreCreateWindow 3. PreSubclassWindow 4. PreTranslateMessage 5. WindowProc 6. OnCommand 7. OnNotify 8. OnChildNotify 9. DefWindowProc 10. DestroyWindow 11. PostNcDestroy CWnd作为MFC中最基本的与窗口打交

构造函数的调用时机(一)

构造函数是C++类的重要组成部分,起着初始化对象的作用.当对象生成的时候,编译器会自动调用对象的构造函数,完成对象的初始化工作.根据对象的不同作用域和声明周期,可以将对象分为一下几种: 1.局部对象 2.堆对象 3.全局对象 4.静态对象 下面我们将以反汇编(VC6.0)的形式,查看局部对象的调用时机 #include <stdio.h> class CDemo { public: CDemo() { m_nInt = 100; } private: int m_nInt; }; int ma

[C++]复制构造函数的定义格式和调用时机

1.复制构造函数定义形式 <类名>::<复制构造函数名>(const <类名>&<对象名>) Test(const Test&t) 2.调用时机 (1)用类的已知对象定义该类的一个正在被创建的对象 Test u; Test t = u;//调用复制构造 (2)对象作为实参传递给函数形参 Test u; Test t(u); (3)对象作为函数返回值 Test u; Test fun() { Test t; return t;//调用复制构造

AppDelegate中几个常用的回调调用时机

本篇文章主要介绍一些UIApplicationDelegate中几个常用的回调方法的调用时机.以帮助你判断哪些方法倒底放到哪个回调中去实现. 1. – (void)applicationDidFinishLaunching:(UIApplication *)application;此方法基本已经弃用,改用第2个方法代替.2. – (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDict

setResult()的调用时机

今天遇到这样一个问题,我在Activity-A中用startActivityForResult()方法启动了Activity-B,并且在B中通过setResult()方法给A返回值,由于某些原因不能在setResult()之后立刻调用finish()函数,只能通过用户按Back键自己退出到A.按理说从B退出回到Aactivity-A过程中,A中的 onActivityResult() 应该被调用, 可是通过log发现,整个操作过程中 onActivityResult() 始终没有被调用. 前后研

(copy)赋值构造函数的4种调用时机or方法

第一种调用方法: demo #include <iostream> using namespace std; class Text { public: Text() // 无参数构造函数 { m_a = 0; m_b = 0; cout << "无参数构造函数" << endl; } Text(int a) // 有参数构造函数 { m_a = a; m_b = 0; cout << "无参数构造函数" <<

自定义View 中一些方法的调用时机

onFinishInflate()函数的调用时机: onFinishInflate() 当View中所有的子控件均被映射成xml后触发 onMeasure(int, int) 确定所有子元素的大小 onLayout(boolean, int, int, int, int) 当View分配所有的子元素的大小和位置时触发 onSizeChanged(int, int, int, int) 当view的大小发生变化时触发 onDraw(Canvas) view渲染内容的细节 onKeyDown(int

java.lang.reflect.InvocationHandler中invoke()方法调用时机

Java中动态代理的实现,关键就是这两个东西:Proxy.InvocationHandler,下面从InvocationHandler接口中的invoke方法入手,简单说明一下Java如何实现动态代理的. invoke方法的完整形式如下: public Object invoke(Object proxy, Method method, Object[] args) throws Throwable       {              method.invoke(obj, args);  

loadView和viewDidLoad及initWithNibName/awakeFromNib/initWithCoder

每个ios开发者对loadView和viewDidLoad肯定都很熟悉,虽然这两个函数使用上真的是非常简单,但是和类似的initWithNibName/awakeFromNib/initWithCoder放在一起还是非常容易让人混淆的. 一.loadView 永远不要主动调用这个函数.view controller会在view的property被请求并且当前view值为nil时调用这个函数.如果你手动创建view,你应该重载这个函数.如果你用IB创建view并初始化view controller