1. 程式人生 > >Swift——(五)Swift中的那些預設值

Swift——(五)Swift中的那些預設值

    在Swift語言中,有很多預設值,這裡將常用的總結,歡迎補充。

    1.函式(方法)形參

   在函式(方法)中,形參預設是常量,不可以在函式(方法)內部進行修改,這主要是為了防止誤操作,防止在呼叫函式(方法)時改變了實參的值,所以使用常量,如果想在函式內部對實參進行修改,可以使用var關鍵字進行標識,但是這並沒有結束,在函式(方法)外部,實參仍然未改變。如果想在函式(方法)呼叫結束之後仍然可以使用修改後的值,需要使用inout關鍵字進行標識,同時不要使用對形參進行標識,在呼叫函式(方法)的時候,傳遞的實參,需要使用"&"進行標識,類似於C、C++中的引用傳遞。
func swap(a: Int, b: Int){  
    let c = a  
//    a = b  // can't assign to `let` value `a`.
//    b = c  // can't assign to `let` value `a`.
} 
    如上程式碼,會出現編譯錯誤,因為a和b預設是常量,不可以修改,如果想修改a和b,可以將程式碼更改如下:
func swap(var a: Int, var b: Int){
    let c = a
    a = b
    b = c
}
var a = 3
var b = 2
swap(a, b) // a = 3, b = 2

在如上程式碼中,形參a和形參b預設都是常量,如果需要a和b的值在函式內部可變,需要使用var關鍵字進行標識,函式實現兩個整數交換,可是在函式外部,兩個整數還是原值,如果想要修改之後的值可以在函式外部訪問,需要新增inout關鍵字,並將var關鍵字刪除。
func swap(inout a: Int, inout b: Int){
    let c = a
    a = b
    b = c
}
var a = 3
var b = 2
swap(&a, &b) // a = 2, b = 3

    2.屬性觀察器

    在Swift中可以為除了lazy的儲存屬性(stored property)和繼承來的屬性設定屬性觀察器,來觀察屬性值的變化,觀察器有兩種,willSet和didSet。willSet在屬性值被改變之前呼叫,didSet在屬性值被改變之後進行呼叫。    注:這裡說的是改變,而不是設定,因為在初始化的時候,是不會呼叫這兩個函式的。並且如果在didSet中,修改了屬性值,也不會再次呼叫willSet和didSet。屬性觀察器,willSet中,即將設定的值預設為newValue(可以自己設定引數名),didSet中,設定之前的值預設為oldValue(可以自己設定引數名)。
class StepCounter {
    var totalSteps: Int = 0
    willSet(newTotalSteps){
        println("About to set totalSteps to \(newTotalSteps)") // you can use newValue if you does not set a name with newTotalSteps
    }

    didSet{
        if totalSteps > oldValue {
            println("Added \(totalSteps - oldValue) steps")
        }
    }
}

let stepCounter = StepCounter() // no output since it is the initialiser, not change the value.
stepCounter.totalSteps = 200 // print both the willSet's and didSet's output.

    在如上的程式碼中,willSet設定了新的引數名:newTotalSteps,didSet使用預設引數名:oldValue。

    3.可選型別

    這裡先進行宣告,在Swift中,可選型別是和其它型別不一樣的(好像廢話一樣),例如:Int和Int?是完全不同的型別,如果想使用Int?型別的值,需要進行可選繫結或者強制解析(在進行強制解析的時候要確保該可選型別當前有值,否則會產生執行時錯誤),才能得到可選型別真正的值。
class Optional{
    var a: Int?
    var b: Int
}

    在如上程式碼中,變數a是有預設值nil的,如果想獲得a的值,需要使用如下程式碼。
a = 10
// optional binding.
if let c = a {
    println("\(c)")
} else {
    println("a is nil")
}

// forced unwrapping, might cause an runtime error if a is nil.
let d = a!

    4.計算屬性的setter

    在計算屬性中,屬性的setter中,將要設定的新值預設為newValue。
struct Circle {
    var radius: Float
    var diameter: Float {
        get{
            return 2.0 * radius
        }
        set{
            radius = newValue / 2.0
        }
    }
}
    如上程式碼中,沒有設置引數名,使用預設的值:newValue。為了便於理解,可以設定新的引數名。
struct Circle {
    var radius: Float
    var diameter: Float {
        get{
            return 2.0 * radius
        }
        set(newDiameter){
            radius = newDiameter / 2.0
        }
    }
}

——————————Update 2014.06.30——————————

    5.構造器

    在Swift中,因為構造器在括號前沒有函式名來標識構造器,所以構造器中的引數對構造器很重要,因此Swift預設為構造器提供了和內部引數名相同的外部引數名。從而在呼叫的使用也必須使用外部引數名。
struct Color {
    let red = 0.0, green = 0.0, blue = 0.0
    init(red: Double, green: Double, blue: Double) {
        self.red = red
        self.green = green
        self.blue = blue
    }
}

let magenta = Color(red: 1.0, green: 0.0, blue: 1.0)
// let veryGreen = Color(0.0, 1.0, 0.0) // will result compile error.