iOS 生命週期

來源:互聯網
上載者:User

標籤:執行個體   fun   ida   其他   ima   release   ram   can   exe   

空閑時間想總結下生命週期這塊,建立一個test項目,先看一下AppDelegate類方法的調用,在所有的方法中加入

NSLog(@"--- %s ---",__func__);列印方法名

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

    // Override point for customization after application launch.

    

    NSLog(@"--- %s ---",__func__);

    

    return YES;

}

 

 

- (void)applicationWillResignActive:(UIApplication *)application {

    // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.

    // Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.

    NSLog(@"--- %s ---",__func__);

}

 

 

- (void)applicationDidEnterBackground:(UIApplication *)application {

    // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.

    // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.

    NSLog(@"--- %s ---",__func__);

}

 

 

- (void)applicationWillEnterForeground:(UIApplication *)application {

    // Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.

    NSLog(@"--- %s ---",__func__);

}

 

 

- (void)applicationDidBecomeActive:(UIApplication *)application {

    // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.

    NSLog(@"--- %s ---",__func__);

}

 

 

- (void)applicationWillTerminate:(UIApplication *)application {

    // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.

    NSLog(@"--- %s ---",__func__);

}

通過程式啟動,進入後台及從後台喚醒進入前台的操作,查看方法調用順序:

 

程式剛啟動時調用方法:

[AppDelegate application:didFinishLaunchingWithOptions:]

[AppDelegate applicationDidBecomeActive:]  //程式被啟用

程式進入後台時調用方法:

[AppDelegate applicationWillResignActive:] //程式取消啟用狀態

[AppDelegate applicationDidEnterBackground:] //程式進入後台

從後台喚醒進入前台時調用方法:

[AppDelegate applicationWillEnterForeground:] //程式進入前台

[AppDelegate applicationDidBecomeActive:] //程式被啟用

 

分析:

1.application:didFinishLaunchingWithOptions:
程式首次已經完成啟動時執行,一般在這個函數裡建立window對象,將程式內容通過window呈現給使用者。

2.applicationWillResignActive(非活動)

程式將要失去Active狀態時調用,比如有電話進來或者按下Home鍵,之後程式進入後台狀態,對應的applicationWillEnterForeground(即將進入前台)方法。

該函數裡面主要執行操作:
a . 暫停正在執行的任務
b. 禁止計時器
c. 減少OpenGL ES幀率
d. 若為遊戲應暫停遊戲

3.applicationDidEnterBackground(已經進入後台)
對應applicationDidBecomeActive(已經變成前台)

該方法用來:
a. 釋放共用資源
b. 儲存使用者資料(寫到硬碟)
c. 作廢計時器
d. 儲存足夠的程式狀態以便下次修複;

4.applicationWillEnterForeground(即將進入前台)
程式即將進入前台時調用,對應applicationWillResignActive(即將進入後台)
這個方法用來: 撤銷applicationWillResignActive中做的改變。

5.applicationDidBecomeActive(已經進入前台)
程式已經變為Active(前台)時調用。對應applicationDidEnterBackground(已經進入後台)
注意: 若程式之前在後台,在此方法內重新整理使用者介面

6.applicationWillTerminate
程式即將退出時調用。記得儲存資料,如applicationDidEnterBackground方法一樣。

 

ViewController的生命週期:

建立兩個VC,一個用SB建立,一個純程式碼建立

- (void)viewDidLoad {

    [super viewDidLoad];

    self.title = @"第二頁(SB)";

    self.view.backgroundColor = [UIColor whiteColor];

    NSLog(@"%s", __func__);

    // Do any additional setup after loading the view, typically from a nib.

}

-(instancetype)init{

    

    self = [super init];

    

    NSLog(@"%s", __func__);

    

    return self;

}

 

- (instancetype)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {

    NSLog(@"%s", __func__);

    if (self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]) {

        

    }

    return self;

}

// 如果串連了串聯圖storyBoard 走這個方法

- (instancetype)initWithCoder:(NSCoder *)aDecoder {

    NSLog(@"%s", __func__);

    if (self = [super initWithCoder:aDecoder]) {

        

    }

    return self;

}

 

// xib 載入 完成

- (void)awakeFromNib {

    [super awakeFromNib];

    NSLog(@"%s", __func__);

}

// 載入視圖(預設從nib)

- (void)loadView {

    NSLog(@"%s", __func__);

    self.view = [[UIView alloc] initWithFrame:[UIScreen mainScreen].bounds];

    self.view.backgroundColor = [UIColor redColor];

}

//視圖將要出現

- (void)viewWillAppear:(BOOL)animated {

    NSLog(@"%s", __func__);

    [super viewWillAppear:animated];

}

// view 即將布局其 Subviews

- (void)viewWillLayoutSubviews {

    NSLog(@"%s", __func__);

    [super viewWillLayoutSubviews];

}

 

// view 已經布局其 Subviews

- (void)viewDidLayoutSubviews {

    NSLog(@"%s", __func__);

    [super viewDidLayoutSubviews];

}

 

//視圖已經出現

- (void)viewDidAppear:(BOOL)animated {

    NSLog(@"%s", __func__);

    [super viewDidAppear:animated];

}

 

//視圖將要消失

- (void)viewWillDisappear:(BOOL)animated {

    NSLog(@"%s", __func__);

    [super viewWillDisappear:animated];

}

 

//視圖已經消失

- (void)viewDidDisappear:(BOOL)animated {

    NSLog(@"%s", __func__);

    [super viewDidDisappear:animated];

}

 

 

- (void)didReceiveMemoryWarning {

    [super didReceiveMemoryWarning];

    NSLog(@"%s", __func__);

    // Dispose of any resources that can be recreated.

}

根據列印結果可以看出方法的執行順序,SB建立的:

2018-03-26 13:46:48.268882+0800 test[4659:680728] -[SecondViewController initWithCoder:]

2018-03-26 13:46:48.269376+0800 test[4659:680728] -[SecondViewController awakeFromNib]

2018-03-26 13:46:48.270668+0800 test[4659:680728] -[SecondViewController loadView]

2018-03-26 13:46:48.271432+0800 test[4659:680728] -[SecondViewController viewDidLoad]

2018-03-26 13:46:48.271676+0800 test[4659:680728] -[SecondViewController viewWillAppear:]

2018-03-26 13:46:48.281261+0800 test[4659:680728] -[SecondViewController viewWillLayoutSubviews]

2018-03-26 13:46:48.281423+0800 test[4659:680728] -[SecondViewController viewDidLayoutSubviews]

2018-03-26 13:46:48.783592+0800 test[4659:680728] -[SecondViewController viewDidAppear:]

 

純程式碼建立的列印順序為:

2018-03-26 13:47:19.564963+0800 test[4659:680728] -[ThirdViewController initWithNibName:bundle:]

2018-03-26 13:47:19.565357+0800 test[4659:680728] -[ThirdViewController init]

2018-03-26 13:47:19.566861+0800 test[4659:680728] -[ThirdViewController loadView]

2018-03-26 13:47:19.567676+0800 test[4659:680728] -[ThirdViewController viewDidLoad]

2018-03-26 13:47:19.568003+0800 test[4659:680728] -[ThirdViewController viewWillAppear:]

2018-03-26 13:47:19.580727+0800 test[4659:680728] -[ThirdViewController viewWillLayoutSubviews]

2018-03-26 13:47:19.580972+0800 test[4659:680728] -[ThirdViewController viewDidLayoutSubviews]

2018-03-26 13:47:20.084203+0800 test[4659:680728] -[ThirdViewController viewDidAppear:]



** 分析 **
1.initWithNibName:bundle:
初始化UIViewController,執行關鍵資料初始化操作,非StoryBoard建立UIViewController都會調用這個方法。
** 注意: 不要在這裡做View相關操作,ViewloadView方法中才初始化。**

2. initWithCoder:
如果使用StoryBoard進行視圖管理,程式不會直接初始化一個UIViewControllerStoryBoard會自動初始化或在segue被觸發時自動初始化,因此方法initWithNibName:bundle不會被調用,但是initWithCoder會被調用。

3. awakeFromNib
awakeFromNib方法被調用時,所有視圖的outletaction已經串連,但還沒有被確定,這個方法可以算作適合視圖控制器的執行個體化配合一起使用的,因為有些需要根據使用者喜好來進行設定的內容,無法存在storyBoardxib中,所以可以在awakeFromNib方法中被載入進來。

4. loadView
當執行到loadView方法時,如果視圖控制器是通過nib建立,那麼視圖控制器已經從nib檔案中被解檔並建立好了,接下來任務就是對view進行初始化。

loadView方法在UIViewController對象的view被訪問且為空白的時候調用。這是它與awakeFromNib方法的一個區別。
假設我們在處理記憶體警告時釋放view屬性:self.view = nil。因此loadView方法在視圖控制器的生命週期內可能被調用多次。
loadView方法不應該直接被調用,而是由系統調用。它會載入或建立一個view並把它賦值給UIViewControllerview屬性。

在建立view的過程中,首先會根據nibName去找對應的nib檔案然後載入。如果nibName為空白或找不到對應的nib檔案,則會建立一個空視圖(這種情況一般是純程式碼)

注意:在重寫loadView方法的時候,不要調用父類的方法。

5. viewDidLoad
loadViewview載入記憶體中,會進一步調用viewDidLoad方法來進行進一步設定。此時,視圖層次已經放到記憶體中,通常,我們對於各種初始化資料的載入,初始設定、修改約束、移除視圖等很多操作都可以這個方法中實現。

視圖層次(view hierachy):因為每個視圖都有自己的子視圖,這個視圖層次其實也可以理解為一顆樹狀的資料結構。而樹的根節點,也就是根視圖(root view),在UIViewController中以view屬性。它可以看做是其他所有子視圖的容器,也就是根節點。
6. viewWillAppear
系統在載入所有的資料後,將會在螢幕上顯示視圖,這時會先調用這個方法,通常我們會在這個方法對即將顯示的視圖做進一步的設定。比如,設定裝置不同方向時該如何顯示;設定狀態列方向、設定視圖顯示樣式等。

另一方面,當APP有多個視圖時,上下級視圖切換是也會調用這個方法,如果在調入視圖時,需要對資料做更新,就只能在這個方法內實現。

7. viewWillLayoutSubviews
view 即將布局其Subviews。 比如viewbounds改變了(例如:狀態列從不顯示到顯示,視圖方向變化),要調整Subviews的位置,在調整之前要做的工作可以放在該方法中實現

8.viewDidLayoutSubviews
view已經布局其Subviews,這裡可以放置調整完成之後需要做的工作。

9. viewDidAppear
在view被添加到視圖層級中以及多視圖,上下級視圖切換時調用這個方法,在這裡可以對正在顯示的視圖做進一步的設定。

10.viewWillDisappear
在視圖切換時,當前視圖在即將被移除、或被覆蓋是,會調用該方法,此時還沒有調用removeFromSuperview

11. viewDidDisappear
view已經消失或被覆蓋,此時已經調用removeFromSuperView;

12. dealloc
視圖被銷毀,此次需要對你在initviewDidLoad中建立的對象進行釋放。

13.didReceiveMemoryWarning
在記憶體足夠的情況下,app的視圖通常會一直儲存在記憶體中,但是如果記憶體不夠,一些沒有正在顯示的viewController就會收到記憶體不足的警告,然後就會釋放自己擁有的視圖,以達到釋放記憶體的目的。但是系統只會釋放記憶體,並不會釋放對象的所有權,所以通常我們需要在這裡將不需要顯示在記憶體中保留的對象釋放它的所有權,將其指標置nil



視圖的生命曆程
  • [ViewController initWithCoder:][ViewController initWithNibName:Bundle]: 首先從歸檔檔案中載入UIViewController對象。即使是純程式碼,也會把nil作為參數傳給後者。
  • [UIView awakeFromNib]: 作為第一個方法的助手,方法處理一些額外的設定。
  • [ViewController loadView]:建立或載入一個view並把它賦值給UIViewControllerview屬性。
    -[ViewController viewDidLoad]: 此時整個視圖層次(view hierarchy)已經放到記憶體中,可以移除一些視圖,修改約束,載入資料等。
  • [ViewController viewWillAppear:]: 視圖載入完成,並即將顯示在螢幕上。還沒設定動畫,可以改變當前螢幕方向或狀態列的風格等。
  • [ViewController viewWillLayoutSubviews]即將開始子視圖位置布局
  • [ViewController viewDidLayoutSubviews]用於通知視圖的位置布局已經完成
  • [ViewController viewDidAppear:]:視圖已經展示在螢幕上,可以對視圖做一些關於展示效果方面的修改。
  • [ViewController viewWillDisappear:]:視圖即將消失
  • [ViewController viewDidDisappear:]:視圖已經消失
  • [ViewController dealloc:]:視圖銷毀的時候調用


參考連結:https://www.jianshu.com/p/d60b388b19f5

iOS 生命週期

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.