Swift中的可选类型

//MARK:-

//MARK:- 可选类型的介绍

/*

1、在Swift开发中,nil也是一个特殊的类型,因为和真实的类型不匹配是不能赋值的(Swift是强类型语言)

2、可选类型的optionals有两种状态值:空值、有值

 

3、可选类型的本质其实就是一个枚举

    None 没有值

    Some 有值

4、格式: Optional<类型>  或 在类型后面加上?号

    由于可选类型在Swift中随处可见, 所以系统做了一个语法糖, 在类型后面加上?

5、目的: 安全, 不管在什么时候访问都是有意义的

   普通变量和可选类型的区别, 普通变量只有一种状态, 有值

*/

 

//MARK:-

//MARK:- 定义可选类型

    //1、基本写法

    var name1 : Optional<String> = nil

    //2、语法糖(常用)

    var name2 : Int? = Int("asdf")

    print(name1,name2)

    //3、给可选类型赋值

    name1 = "ptf"

    print(name1)//因为打印出来的是可选类型,所以会带有optional

 

//MARK:-

//MARK:- 取出可选类型的值(解包)

/*

    会将name1中的整型值强制拿出来 换句话说就是告诉编译器name1一定有值, 因为可选类型有两种状态有值和没有值, 所以需要告诉编译器到底有没有值

    注意:如果强制解析name1, 但是name1中没有值时会引发一个运行时错误

    建议:在对可选类型进行解包之前,先判断可选类型是否等于nil

*/

    print(name1!)

    if name1 != nil {

    print(name1!)

    }

 

 

//MARK:-

//MARK:- 可选绑定

/*

    1.判断name是否有值,如果没有值,直接不执行{}

    2.如果name有值,那么系统会对name进行解包,并且将解包后的结果赋值Name

*/

    if let name2 = name1 {

        print(name2)

    }

//MARK:可选类型的真实场景应用

    //方式一:

    let url1 : NSURL? = NSURL(string: "http://www.cnblogs.com/skyPeat/")

    //方式二:使用类型推导

    let url = NSURL(string: "http://www.cnblogs.com/skyPeat/")

 

    if let url = url {

        let request = NSURLRequest(URL: url)

        print(url)

        print(request)

    }

    //如果可以保证返回值一定有值,那么是可以强制解包的,如果没有值程序就会崩掉

    //let path = NSBundle.mainBundle().pathForResource("www", ofType: nil)

    //print(path)!

 

//MARK:-

//MARK:- 可选链

/*

1、可选连的概念:通过可选类型的变量来调用相应的属性和方法,可选链的返回值是一个可选值

2、格式:  可选值?.属性    可选值?.方法

*/

//创建类

    class Person {

        var name : String?

        var dog : Dog?

    }

 

    class Dog {

        var name : String?

        var toy : Toy?

    }

    class Toy {

        var price : Double?

        func rolating(){

            print("rotating")

        }

    }

//创建人、狗、玩具的对象

    let person = Person()

    person.name = "ptf"

    let dog = Dog()

    dog.name = "wangcai"

    let toy = Toy()

    //toy.price = 100

    person.dog = dog

    dog.toy = toy

 

//可选链

    //person.dog?.toy?.price = 1000

    let price = person.dog?.toy?.price

    print(price)

    person.dog?.toy?.rolating()

 

//MARK:-

//MARK:- 可选链调用下标索引

/*

格式:可选值?[]

*/

 

struct Student {

    var name:String = "lnj"

    var math:Double = 99.0

    var chinese:Double = 99.0

    var english:Double = 99.0

    

    // 要想实现下标访问, 必须实现subscript方法

    // 如果想要通过下标访问, 必须实现get方法

    // 如果想要通过下表赋值, 必须实现set方法

    subscript(course:String) ->Double?{

        get{

            switch course{

            case "math":

                return math

            case "chinese":

                return chinese

            case "english":

                return english

            default:

                return nil

            }

        }

        set{

            switch course{

            case "math":

                // 因为返回的是可选类型

                math = newValue!

            case "chinese":

                chinese = newValue!

            case "english":

                english = newValue!

            default:

                print("not found")

            }

            

        }

    }

}

var stu:Student? = Student()

// 可选链调用下标索引不需要., 直接在问号后面写上[]即可

print(stu?["math"])

 

//var arr:Array? = [1, 2, 3, 4]

//print(arr?[1])

 

// 利用可选链赋值. 注意: 早期版本中不能利用可选链赋值

stu?.name = "ww"

print(stu?.name)

//  利用可选链给下标赋值

stu?["math"] = 88

print(stu?["math"])

 

// 判断赋值操作是否成功, 可选链的赋值操作也有返回值

// 如果赋值成功会返回一个可选类型, 返回()?也就是Viod? 代表成功. 返回nil代表失败

//let res: = stu?.name = "zl"

//let res: ()? = stu?.name = "zl"

//let res: Void? = stu?.name = "zl"

stu = nil

let res: Void? = stu?.name = "zl"

print(res)

 

 

/*

多层可选链:

单层:可选值?.属性

多层:可选值?.属性.属性?.属性 或者 可选值?.属性?.属性?.属性

*/

class A {

    var name:String = "lnj"

}

class B{

    var a1:A?

}

class C{

    var b1:B = B()

}

class D{

    var c1: C?

}

 

var a1 = A()

var b1 = B()

var c1 = C()

var d1 = D()

 

d1.c1 = c1

//b1.a1 = a1

// 通过d直接给b赋值

// 由于D中的C是可选值, 所以需要在C后面加上?

d1.c1?.b1.a1 = a1

// 通过d直接获取a中的name

// 其实只需要在可选值后面加上问号即可, 如果可选值不存在, 那么后面的链失效

print(d1.c1?.b1.a1?.name)

 

 

 

 

 

 

 

 

 

 

 

 

 

 

import Foundation

//MARK:-

//MARK:- 可选类型的介绍

/*

1、在Swift开发中,nil也是一个特殊的类型,因为和真实的类型不匹配是不能赋值的(Swift是强类型语言)

2、可选类型的optionals有两种状态值:空值、有值

 

3、可选类型的本质其实就是一个枚举

    None 没有值

    Some 有值

4、格式: Optional<类型>  或 在类型后面加上?号

    由于可选类型在Swift中随处可见, 所以系统做了一个语法糖, 在类型后面加上?

5、目的: 安全, 不管在什么时候访问都是有意义的

   普通变量和可选类型的区别, 普通变量只有一种状态, 有值

*/

 

//MARK:-

//MARK:- 定义可选类型

    //1、基本写法

    var name1 : Optional<String> = nil

    //2、语法糖(常用)

    var name2 : Int? = Int("asdf")

    print(name1,name2)

    //3、给可选类型赋值

    name1 = "ptf"

    print(name1)//因为打印出来的是可选类型,所以会带有optional

 

//MARK:-

//MARK:- 取出可选类型的值(解包)

/*

    会将name1中的整型值强制拿出来 换句话说就是告诉编译器name1一定有值, 因为可选类型有两种状态有值和没有值, 所以需要告诉编译器到底有没有值

    注意:如果强制解析name1, 但是name1中没有值时会引发一个运行时错误

    建议:在对可选类型进行解包之前,先判断可选类型是否等于nil

*/

    print(name1!)

    if name1 != nil {

    print(name1!)

    }

 

 

//MARK:-

//MARK:- 可选绑定

/*

    1.判断name是否有值,如果没有值,直接不执行{}

    2.如果name有值,那么系统会对name进行解包,并且将解包后的结果赋值Name

*/

    if let name2 = name1 {

        print(name2)

    }

//MARK:可选类型的真实场景应用

    //方式一:

    let url1 : NSURL? = NSURL(string: "http://www.cnblogs.com/skyPeat/")

    //方式二:使用类型推导

    let url = NSURL(string: "http://www.cnblogs.com/skyPeat/")

 

    if let url = url {

        let request = NSURLRequest(URL: url)

        print(url)

        print(request)

    }

    //如果可以保证返回值一定有值,那么是可以强制解包的,如果没有值程序就会崩掉

    //let path = NSBundle.mainBundle().pathForResource("www", ofType: nil)

    //print(path)!

 

//MARK:-

//MARK:- 可选链

/*

1、可选连的概念:通过可选类型的变量来调用相应的属性和方法,可选链的返回值是一个可选值

2、格式:  可选值?.属性    可选值?.方法

*/

//创建类

    class Person {

        var name : String?

        var dog : Dog?

    }

 

    class Dog {

        var name : String?

        var toy : Toy?

    }

    class Toy {

        var price : Double?

        func rolating(){

            print("rotating")

        }

    }

//创建人、狗、玩具的对象

    let person = Person()

    person.name = "ptf"

    let dog = Dog()

    dog.name = "wangcai"

    let toy = Toy()

    //toy.price = 100

    person.dog = dog

    dog.toy = toy

 

//可选链

    //person.dog?.toy?.price = 1000

    let price = person.dog?.toy?.price

    print(price)

    person.dog?.toy?.rolating()

 

//MARK:-

//MARK:- 可选链调用下标索引

/*

格式:可选值?[]

*/

 

struct Student {

    var name:String = "lnj"

    var math:Double = 99.0

    var chinese:Double = 99.0

    var english:Double = 99.0

    

    // 要想实现下标访问, 必须实现subscript方法

    // 如果想要通过下标访问, 必须实现get方法

    // 如果想要通过下表赋值, 必须实现set方法

    subscript(course:String) ->Double?{

        get{

            switch course{

            case "math":

                return math

            case "chinese":

                return chinese

            case "english":

                return english

            default:

                return nil

            }

        }

        set{

            switch course{

            case "math":

                // 因为返回的是可选类型

                math = newValue!

            case "chinese":

                chinese = newValue!

            case "english":

                english = newValue!

            default:

                print("not found")

            }

            

        }

    }

}

var stu:Student? = Student()

// 可选链调用下标索引不需要., 直接在问号后面写上[]即可

print(stu?["math"])

 

//var arr:Array? = [1, 2, 3, 4]

//print(arr?[1])

 

// 利用可选链赋值. 注意: 早期版本中不能利用可选链赋值

stu?.name = "ww"

print(stu?.name)

//  利用可选链给下标赋值

stu?["math"] = 88

print(stu?["math"])

 

// 判断赋值操作是否成功, 可选链的赋值操作也有返回值

// 如果赋值成功会返回一个可选类型, 返回()?也就是Viod? 代表成功. 返回nil代表失败

//let res: = stu?.name = "zl"

//let res: ()? = stu?.name = "zl"

//let res: Void? = stu?.name = "zl"

stu = nil

let res: Void? = stu?.name = "zl"

print(res)

 

 

/*

多层可选链:

单层:可选值?.属性

多层:可选值?.属性.属性?.属性 或者 可选值?.属性?.属性?.属性

*/

class A {

    var name:String = "lnj"

}

class B{

    var a1:A?

}

class C{

    var b1:B = B()

}

class D{

    var c1: C?

}

 

var a1 = A()

var b1 = B()

var c1 = C()

var d1 = D()

 

d1.c1 = c1

//b1.a1 = a1

// 通过d直接给b赋值

// 由于D中的C是可选值, 所以需要在C后面加上?

d1.c1?.b1.a1 = a1

// 通过d直接获取a中的name

// 其实只需要在可选值后面加上问号即可, 如果可选值不存在, 那么后面的链失效

print(d1.c1?.b1.a1?.name)

 

你可能感兴趣的:(Swift中的可选类型)