Swift3.0語法2


(一)可選項:

 

(二)懶加載:

OC開發中,懶加載一般自定義控件。在Swift中,懶加載還是需要用的,可以保證控件延遲創建,還能避免處理控件解包。如果直接定義控件var label = UILabel,根據代碼從上到下,會讓控件在ViewDidLad之前就提前創建了。所以需要懶加載。OC中懶加載就是Get方法,Swift直接lazy var。當然也可以private lazy var來限定作用域。

1)簡單的懶加載:

  (2)完整的懶加載:()就是函數執行,就是一個特殊的閉包,所以懶加載本質是一個閉包。一般不這么寫。

  

3OCSwift區別

*OC

    

    OC是等於nil時候就懶加載

    

  

  當labelnil的時候就在此調用。在ios6中,didReceiveMemoryWarning是不清理視圖的。

 

 

  

此時釋放的時候就會報錯。因為定義的時候沒有?,就是一定有值得。

那么如果定義時候加? 一旦label = nil,也不會在執行懶加載了!因為懶加載根本沒寫如果是空就創建。

懶加載只會在第一次調用的時候執行閉包。Swift中一定注意不要主動清理視圖或控件,因為懶加載不會創建了(例如內存警告別干掉控件,干掉了在也用不成了,因為懶加載就一次)

(三)計算型屬性(只讀):

1)getter/setter(開發不用):

 

 // 開發一般不用,還給搞一個_name。
        // swift一般不會重寫getter和setter
        private var _name: String? // 假裝的一個值
        var name: String? { get{return _name}  set{_name = newValue}} // get返回成員變量 set記錄成員變量
    
        override func viewDidLoad() {
            super.viewDidLoad()
            
            demo()
        }

2)計算型屬性:readOnly只讀:OC中重寫get。Swift也是重寫get,不管set就可以。

 

// 只讀,此時set賦值時候就會報錯
        var name: String? { get{return "ABC"}}
        還有一種簡寫:
        var name: String? { return "ABC"}

 

看這類屬性,是本身不保存內容的,都是通過計算獲得結果。就可以當我就是個沒有參數只有返回值的函數!!我每次return值給你我的任務就完成了。每次你調用我這個屬性的時候,我都會進行一次計算!都會執行我的代碼然后return給你。我自身不存儲的。

 

  (3)懶加載和計算型屬性的區別:

4)存儲型屬性:需要開辟空間,存儲數據。一般的屬性都是存儲型屬性(懶加載)

5)存儲和計算都可以?或者不加。看情況是不是必選

(四)Swift中設置模型數據:

Swift做好模型后。別的控件拿到模型后,由視圖自己來顯示。此時在didSet里寫。就是替代OCSetter方法。(OCSetter要考慮_成員變量 = 值,而且如果是copy需要.copy,而Swift不需要考慮一切)

(五)命名空間和反射機制

1)命名空間:

*在同一個空間(項目),全局共享。用第三方時,如果直接拖拽,那就從屬於一個空間,很有可能沖突,所以用Cocopod

*動態獲得命名空間(從info.plist加載),命名空間和項目名稱有關系。info的Bundle name其實就是命名空間(一般寫的很奇怪 #ProdectNmae))。

打印info

print(Bundle.main.infoDictionary)

 

    賦值

        // 獲取命名空間的值,可選
         let str = Bundle.main.infoDictionary?["CFBundleName"] as? String ?? ""
                
         let con = NSClassFromString(str + "." + "ViewController") as? UIViewController.Type

2)反射機制:對於任何類都可以知道類的所有屬性和方法,對於任何對象都可以調用任何屬性和方法,這種動態獲取的信息和動態調用對象屬性方法的功能成java的反射機制(Swift也有了)

*OC中利用反射機制

*Swift中利用反射機制類似。工作中用的很多很多。

場景:AppDelegateOC中也用過,利用NSClassFromString獲得類,然后設置根控制器。但是Swift中多了一個命名空間寫法。)

 

        func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
            
                
                window = UIWindow(frame: UIScreen.main.bounds)
                
                // 依據String名字拿到控制器(添加項目名稱,命名空間,不能有數字和特殊符號)
                // 返回的是AnyClass? 需要as?強轉
                // 控制器添加Type類型
                let rootControl = NSClassFromString("SwiftyDemo.ViewController") as? UIViewController.Type
                
                let vc = rootControl?.init()
                
                window?.rootViewController = vc
                
                window?.makeKeyAndVisible()
                 
                return true
    }

 

第三方框架,用了很多反射機制和工廠方法,為了實現大量的解耦和封裝,很麻煩。一個方法可能跳10個方法10個控制器才寫了一個加法。但是如果涉及高級開發和封裝,必須要經過這一步。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM