专题一——Swift2.2语言预览

专题一——Swift2.2语言预览

一、引言

        本系列专题是我通过阅读Swift2.2语言开发文档,翻译总结加上自己的理解整理而成。其中大部分结构和内容都来自开发文档,有疏漏和错误之处,还望更多朋友指出,共同交流进步,我的QQ:316045346。

二、从HelloWorld开始

        在学习很多编程语言时,都是从HelloWorld入门,下面代码就是一个完整的HelloWorld程序:

?


1

print("Hello, World!")

分析上面代码,可以发现Swift语言的3个十分明显的特点:

1.开发者不需要引入输入输出相关的函数库。

2.在编写代码时,不需要在语句的结尾处添加分号。

3.全局的代码就是程序的入口,不需要类似C系语言的main()方法来作为程序入口。

三、常量与变量

        常量和变量是编程语言中最基础的两类数据类型,常量可以理解为为某个值起一个特定的名字,常量通常提供给开发者用于某些只赋值一次但却在程序中多处使用的量值。变量也可以进行多次修改。分别使用let和var创建常量和变量。例如:

?


1

2

3

let letValue = 4

var varValue = 8

varValue = 16

开发者在进行常量和变量的创建时,并不需要制定类型,编译器与根据第一次赋值的类型来推断出常量或者变量的类型,然而这并不是说Swift语言不严格要求变量或常量的类型,一旦编译器推断了值的类型,之后开发者若要修改变量,则必须严格遵守既定的变量类型,否则编译器会报错。

        如果开发者第一次对变量或常量进行的赋值不能够使编译器正确的推断出常量或变量的类型,开发者也可以通过冒号后跟类型的方式来强制定义变量或常量的类型,如下:

?


1

2

var varValue:Float = 8

varValue = 16.0

在Swift语言中,不存在隐式转换的概念,这也是Swift语言更加安全的特性之一,这样的设计可以保证变量在任何时候类型都被明确的指定。在进行类型转换时,可以通过类实例化的方式进行,示例如下:

?


1

2

3

4

//Float值转成Int

letValue+Int(varValue)

//Int转为Float

Float(letValue)+varValue

对于在字符串中使用其他类型的变量,Swift语言提供了一种更加便捷的写法,使用\()的方式来转换,小括号内为变量的名称,例如:

?


1

2

3

var strValue = "Hello"

//Hello16.0

strValue+"\(varValue)"

四、数组与字典

        数组与字典是最常用的两种数据集合,在Swift语言中,使用[]来创建数组或字典,示例如下:

?


1

2

var array = [1,2,3]

var dic = [1:"one",2:"two",3:"three"]

同Int,Float类型的数据一样,数组和字典在第一次赋值时,也会根据赋值的类型来推断出变量类型,开发者同样也可以强制指定,如下:

?


1

2

var array:[Int] = [1,2,3]

var dic:[Int:String] = [1:"one",2:"two",3:"three"]

Swift允许创建或者重新赋值为空的数据或者字典,但是这有一个前提条件,被赋值为空的数据或字典必须是类型确定的,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

//这样写会报错

//var errorArray = []

//创建空的数据集合

//方式一

var array:[Int] = []

var dic:[Int:String] = [:]

//方式二

var array2 = [Int]()

var dic2 = [Int:String]()

//方式三

var array3 = [1]

var dic3 = [1:"1"]

array3 = []

dic3 = [:]

五、optional类型的值

        在理解optional类型的值之前,我们可以先来看一段C代码:

?


1

2

3

4

5

6

int a=1;

if(a){

     

}else{

     

}

上面这段代码对于C语言来说完全没有问题,当a为非0值时,就代表条件为真,在Swift语言中则不同,if选择语句中的条件必须为Bool类型的值,因此,对于某些可以为空的值,Swift中提供了optional类型,这种类型相当于对其他实际类型进行了包装,如果有值,则他拆包后为相应类型的值,如果没有值,则为空值nil。示例如下:

?


1

2

3

4

var optionalString: String? = "Hello"

if optionalString == nil {

     

}

在Swift中,当if与let共同使用时,将会构成一种更加奇特的语法方式,这种方式对于处理optional类型的值十分方便,示例如下:

?


1

2

3

4

5

6

7

8

9

10

/*

 if let 后面赋值为optional类型的值有这样的效果

 如果optional的值不为nil 则会走if条件为真的语句块并且将optional变量的值赋值给let常量 可以在if为真的语句块中使用

 如果optional的值为nil 则会走else语句块 并且name常量被释放 不能再else块中使用

*/

if let name=optionalName {

    greeting = "Hello, \(name)"

}else{

    print(greeting)

}

除了if let语法外,还有一种方式可以用来处理optional类型的值,示例如下:

?


1

2

var greeting = "Hello!"

greeting = "Hello" + (optionalString ?? "")

??运算符用来为optional类型的值设置一个默认值,如果optional值为nil,则会使用后面设置的默认值来代替。

        Swift语言的switch语句相比于C系的语言要强大的多,其不只可以用于判断整型,其可以处理任意类型的数据,同样,它也不只限于比较是否相等的运算,其可以支持各种负责运算,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

let vegetable = "red pepper"

switch vegetable {

case "celery":

    print("Add some raisins and make ants on a log.")

case "cucumber""watercress":

    print("That would make a good tea sandwich.")

case let x where x.hasSuffix("pepper"):

    print("Is it a spicy \(x)?")

default:

    print("Everything tastes good in soup.")

}

如果匹配上了一个case,程序会结束switch选择,各个case之间是互斥的。

六、循环语句

        Swift2.2中,弃用了for i;param;param{}格式的循环语句,提供给开发者使用的循环语句主要有3种。

1.for in语句

for in语句多用于快速遍历字典,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

let interestingNumbers = [

    "Prime": [2, 3, 5, 7, 11, 13],

    "Fibonacci": [1, 1, 2, 3, 5, 8],

    "Square": [1, 4, 9, 16, 25],

]

var largest = 0

for (kind, numbers) in interestingNumbers {

    for number in numbers {

    //找出最大值

        if number > largest {

            largest = number

        }

    }

}

print(largest)

在for in循环中可以使用一个索引来指定循环次数,通过这种方式可以实现有序的遍历操作,示例如下:

?


1

2

3

for in 0..<10 {

    print(i)

}

2.while语句

while语句用于条件循环,直到不再满足某个条件为止,示例如下:

?


1

2

3

4

5

var n = 2

while n < 100 {

    n = n * 2

}

print(n)

3.repeat {}while语句

repeat{}while语句与C语言中的do{}while作用相同,保证至少循环一次。示例如下:

?


1

2

3

4

5

var m = 2

repeat {

    m = m * 2

while m < 100

print(m)

七、函数与闭包

        Swift中的函数使用关键字func来标识,格式如下:

func name(param1,param2...)->returnValue{}

示例代码如下:

?


1

2

3

4

5

func add(param1:Int,param2:Int) -> Int {

    return param1+param2

}

//下面表达式将返回8

add(5, param2: 3)

我比较了Swift语言与Objective-C、Java语言的函数特点:

        Objective-C实际上并没有函数重载的概念,不同参数的函数实际上拥有不同的函数名,Objective-C的风格将参数名嵌套进函数名中,这样有一个好处,开发者可以通过函数名明确的知道此函数的用途以及每个参数的意义,当然也有其局限性,Objective-C的函数大多十分冗长,不够简洁。

        Java不同参的函数采用重载的方式,这样的效果是,相同的函数名,参入不同的参数则会执行不同的操作,是不同的两个方法,这样的有点是使代码十分简洁,然而对开发者来说并不友好,开发者在开发时不能便捷的看出每个参数的意义和用法。

        个人见解,Swift对函数的设计综合了上面两种语言的有事,参数列表与函数名分离,简化了函数,同时,参数列表中保留了每个参数的名称,使开发者在调用函数时更加直观。

        在Objective-C中,如果需要某个函数返回一组值,开发者通常会需要使用字典或者数组,这样做有一个问题,在调用此函数时,返回值的意义十分模糊,开发者需要明确的知道其中数据的顺序与意义。Swift中可以采用返回元组的方式来处理一组返回值,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

//返回一组数据的函数

func calculateStatistics(scores: [Int]) -> (min: Int, max: Int, sum: Int) {

    var min = scores[0]

    var max = scores[0]

    var sum = 0

     

    for score in scores {

        if score > max {

            max = score

        else if score < min {

            min = score

        }

        sum += score

    }

     

    return (min, max, sum)

}

//元组数据

let statistics = calculateStatistics([5, 3, 100, 3, 9])

//通过名称取元组中的最大值

print(statistics.max)

//通过角标取元组中的最小值

print(statistics.0)

        对于可变参数个数的函数,在Objective-C中,开发者大多会采用va_list指针的方式实现,示例如下:

?


1

2

3

4

5

6

7

8

9

10

-(void)myLog:(NSString *)str,...{//省略参数的写法

    va_list list;//创建一个列表指针对象

    va_start(list, str);//进行列表的初始化,str为省略前的第一个参数,及...之前的那个参数

    NSString * temStr = str;

    while (temStr!=nil) {//如果不是nil,则继续取值

         NSLog(@"%@",temStr);

         temStr = va_arg(list, NSString*);//返回取到的值,并且让指针指向下一个参数的地址

    }

    va_end(list);//关闭列表指针

}

在Swift语言中,实现这样的函数要简单的多,通过...来进行参数的省略,并且将这些省略的函数包装为数组传入函数内部,示例如下:

?


1

2

3

4

5

6

7

8

9

10

func sumOf(numbers: Int...) -> Int {

    var sum = 0

    //多参被包装为数组

    for number in numbers {

        sum += number

    }

    return sum

}

sumOf()

sumOf(42, 597, 12)

与Java类似,Swift中的函数也支持嵌套操作,嵌套内部的函数可以使用外部的变量,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

func returnFifteen() -> Int {

    var y = 10

    //嵌套函数

    func add() {

        y += 5

    }

    //调用

    add()

    return y

}

returnFifteen()

由于函数也是一种特殊的数据类型,函数也可以作为返回值,示例如下:

?


1

2

3

4

5

6

7

8

func makeIncrementer() -> ((Int) -> Int) {

    func addOne(number: Int) -> Int {

        return 1 + number

    }

    return addOne

}

var increment:((Int)->Int) = makeIncrementer()

increment(7)

一个函数也可以作为另一个函数的参数来使用,示例如下:

?


1

2

3

4

5

6

7

8

9

//参数中有函数

func func1(param1:Int,param2:(count:Int)->Void) {

    param2(count: param1+1)

}

func tmpFunc(count:Int) -> Void {

    print(count)

}

//将函数作为参数传入

func1(3, param2: tmpFunc)

与Objective-C中的block对应,Swift中有闭包的概念来创建一个代码块,可以理解为闭包为没有名字的函数,使用{()in }格式来创建闭包,示例代码如下:

?


1

2

var f:(count:Int)->Void = {(Count) in print(132) }

f(count:0)

通过这种写法,开发者在将函数作为参数传递时,无需再创建中间函数,示例如下:

?


1

2

3

4

5

6

7

8

9

//参数中有函数

func func1(param1:Int,param2:(count:Int)->Void,param3:(count:Int)->Void) {

    param2(count: param1+1)

}

func1(3, param2: { (count) in

        print(count)

    }, param3: { (count) in

        print(count)

})

还有一种更加简单的闭包书写方法,如果闭包类型是确定的,全完可以省略小括号中的参数名称与闭包格式in,使用角标来获取参数,示例如下:

?


1

2

3

4

5

6

//优化前

var f:(a:Int,b:Int)->Bool = {(a,b) in return a>b}

f(a: 3,b: 4)

//优化后

var f:(a:Int,b:Int)->Bool = {$0>$1}

f(a: 3,b: 4)

八、类与属性

        Swift中使用class关键字来定义类,类内部可以声明与定义一些属性与方法,类的实例对象可以通过点语法来调用类的属性和方法,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

class MyClass {

    var count = 100

    let name = "珲少"

    func run() {

        print("run 100 miter")

    }

}

var obj = MyClass()

let count = obj.count

let name = obj.name

obj.run()

类名加括号用于创建类的实例对象,可以通过重写init方法来重写类的默认构造方法,如果这个类有继承的父类,则需要遵守如下3条规则:

1.必须先将子类的属性初始化完成。

2.调用父类的构造方法。

3.修改父类需要修改的属性。

        在Swift中同样也有set和get方法,只是这里的set和get方法与Objective-C中的set和get方法有很大的不同,Objective-C中的get和set方法是截获了属性和存取过程,在其中加入额外的其他操作,Swift中的set和get方法原理上将属性的存取与其他逻辑操作进行了分离,抽象出了一种计算属性,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

class MyClass {

    var count:Int

    //实际上并不存在privateCount属性 通过pricatecount来操作count的值

    var privateCount:Int{

        get{

            return count;

        }

        set {

           count=newValue+100

        }

    }

    let name = "珲少"

    func run() {

        print("run 100 miter")

    }

    init(){

        count=200

    }

}

Swift采用这样的设计思路也有其一定的优化道理,我比较了一下,给大家举一个最简单的例子,在使用Objective-C进行iOS开发时,经常会遇到这样的情况,某个控件中有一个UILabel控件,开发者在不想将控件暴漏在.h文件中的情况下经常会声明一个NSString类型的变量,重写此变量的set方法来完成对UILabel控件的赋值,仔细想来,实际上声明的这个NSString变量完全是多余的,它只是为了用来做中间值得传递,Swift的set和get方法就在这里进行了优化。另外,在set方法中会自动生成一个命名为newValue的变量作为传递进来的值,开发者也可以自定义这个变量的名称,在set后加小括号即可,示例如下:

?


1

2

3

4

5

6

7

8

var privateCount:Int{

        get{

            return count;

        }

        set(myValue) {

           count=myValue+100

        }

    }

        Swift中也提供了监听属性赋值过程的方法,其使用的是willSet与didSet机制,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

class MyClass {

    var count:Int{

        //赋值前执行(除了第一次初始赋值) 将要赋值的值以newValue传入

        willSet{

            print("will set \(newValue)")

        }

        //赋值后执行(除了第一次初始赋值) 原来的值以oldValue传入

        didSet{

           print("did set \(oldValue)")

        }

    }

    let name = "珲少"

    func run() {

        print("run 100 miter")

    }

    init(){

        count=200

    }

}

九、枚举和结构体

        Swift中的枚举和C与Objective-C有很大的差别,在Swift中,枚举也被作为一种数据类型来处理,其中可以添加函数方法。最基本的枚举用法如下所示:

?


1

2

3

4

5

6

7

8

//枚举可以多个case并列 也可以写在一个case中以逗号分隔

enum MyEnum {

    case one

    case tew

    case three

    case Fir,Sec,Thr

}

var em = MyEnum.one

如果变量是类型确定的枚举,在赋值时可以省略枚举名,示例如下:

?


1

var em:MyEnum = .one

Swift中的枚举还有一个原始值的概念,要使用原始值,必须在创建枚举类型时设置原始值的类型,示例如下:

?


1

2

3

4

5

6

7

enum MyEnum:Int {

    case one=1

    case tew

    case three

    case Fir,Sec,Thr

}

var em = MyEnum.one.rawValue

如果原始值是Int类型,则默认从0开始依次递增,开发者也可以手动设置每个枚举值的原始值。同样,也支持使用原始值来创建枚举实例,如下:

?


1

var em = MyEnum(rawValue:1)

通过原始值实例的枚举对象实际上回返回一个optional类型的值,如果传入的原始值参数不能匹配到任何一个枚举case,则可以使用if let结构进行判断处理。

        在枚举中封装方法示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

enum MyEnum:Int {

    case one

    case tew

    case three

    case Fir,Sec,Thr

    func des() {

        switch self {

        case .one:

            print("one")

        default:

            print("else")

        }

    }

}

var em = MyEnum(rawValue:1)

em?.des()

        Swift中的枚举也可以添加附加值,在switch语句中取到对应的枚举类型后,可以获取开发者设置的附加值进行逻辑处理,示例如下:

?


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

enum MyEnum {

//为这个类型天啊及一组附加值

    case one(String,Int)

    case tew

    case three

    case Fir,Sec,Thr

    func des() {

        switch self {

        case .one:

            print("one")

        default:

            print("else")

        }

    }

}

var em = MyEnum.one("第一个元素", 1)

switch em {

//前面的let指定附加值为常量 或者用var指定为变量,括号内为附加值参数名

case let .one(param1, param2):

    print("One param is  \(param1) and two param is  \(param2).")

default:

    print("else")

}

        Swift中使用struct关键字来进行结构体的创建,结构体的功能和类相似,支持属性与方法,但不同的是,结构体在传递时会被赋值,类的实例则会以引用的方式传递。

时间: 2024-03-14 03:46:53

专题一——Swift2.2语言预览的相关文章

Windows8.1预览版支持13种语言

  Windows 8.1预览版将于6月26日到来,不少用户又开始关心系统语言的问题了;其实这本不该是个"问题".比如说,在微软公开测试的Windows8预版中,简体中文何时缺席过呢? Windows8.1预览版会支持13种语言:阿拉伯语.英语(美国).简体中文.繁体中文.法语.德语.日语.韩语.葡萄牙语(巴西).俄罗斯语.西班牙语.瑞典语和土耳其语. 注意事项: • 若你所安装的Windows8.1预览版的语言版本和当前电脑语种不一致,你只能保留文件,而无法保留应用和设置. • 如果

Win8.1预览版支持多种语言版本升级

先前微软发布的官方Windows 8.1预览版仅支持英文(美国)语言,不能安装在携其他语言包的设备上.现在微软终于敞开这扇大门,让使用其他语言包的用户也能通过Windows Store进行Windows 8.1预览版系统的安装和升级操作.      国外媒体报道称,目前相关的Windows 8设备,如果搭载使用英语(美国)之外的语种,系统也将允许用户在Windows Store商店进行Windows 8.1预览版系统的下载和安装操作.所以全球不同地区的用户此刻应当都能享受到8.1预览版系统的尝鲜

Win10预览版ISO镜像文件中怎么添加中文语言包

需要的材料: 1. 英文Win10预览版英文原版ISO镜像: 2. 要集成的中文语言包: 3. ISO打包软件,可用软碟通: 4. 可处理wim映像文件的dism工具.Win8以上版本都已包含,建议在Windows10预览版中操作. 制作步骤: 1. 解压或提取ISO镜像中的sources\install.wim文件 这里假设wim文件路径为:E:\sources\install.wim 2. 挂载wim文件中的第一个映像. 新建挂载目标位置,比如E:\mount.以管理员身份运行CMD,输入以

微软Office2016技术预览版安装图文教程

  今天微软放出了Office2016技术预览版安装包,这种安装包和正式版区别不小,安装操作也有所不同.解压后,发现里面有一个"OfficePreview"文件和"Files"文件夹,此时双击"OfficePreview"文件开始安装.下面小编就为大家带来微软Office2016技术预览版安装图文教程,一起来看看! ▲ 直接打开"OfficePreview",不要通过"Files"文件夹中的文件进行安装 ▲

Windows 8.1预览版首测

  Win8.1作何改变Win9还有多远? Windows 8已经在2012年10月推出,到现在为止不到一年的时间.微 软公司对Win8的后续开发升级在不断地进行之中,而作为Windows 8基础上的一个重要升级更新,Windows 8.1预览版已在6月26日 2013微软Build开发者大会上发布.在Win8.1项目中,微软将实现操作系统升级标准化,以便向用户提供更常规的升级.Windows 8.1具 有承上启下的作用,为未来的Windows 9铺路.那么Win9还有多远?Windows 8.

网页中照片预览导航设计技巧

导航并不只是指常位于网站头部的导航条,路边的指示牌.商场的指示牌等等都是一种导航,可以说导航在生活中无处不在,如果没有这些导航存在,那么我们将迷失,迷失在互联网信息的海洋中,迷失在纵横交错的马路上,迷失在琳琅满目的商品货架之间. 在所谓的WEB2.0风潮疯狂的从国外吹入国内的时候,国外一些成功网站的成功模式也疯狂的吹入到国内的模仿者的眼前.目前在国内关于网络相册方面或者时尚一点是说关于WEB2.0网络相册方面做得比较好的应该算是yupoo了,同时它也是国内模仿flickr模式最像的最成功的--事

C++Builder中自定义预览窗口

Borland C++ Builder是基于C++语言的可视化编程环境,它提供了可重用组件库和一系列RAD设计工具,使得编程者只需用少量的手工代码就可以创建出高效的Windows应用程序,尤其是复杂的数据库访问应用程序,因此深受软件开发人员的喜爱. 在开发数据库访问应用程序时,会经常涉及到报表的打印问题.C++ Builder中提供了Quick Report(快速报表)组件供编程人员设计报表.Quick Report是挪威的QuSoft AS公司专门为C++ Builder设计的用于制作报表的一

Office2015预览版可自选版本

  作为下代Office,Office2015预览版全新加入Tell Me辅助功能.暗黑主题.基于元数据的自动旋转图像.先加载文档后加载图表.全新Excel数据模型.缩短Outlook同步时间等新特性,预计在明年随Win9正式发布. 这次曝光的组图中,Office2015预览版仍以Office16代号命名,安装启动界面依旧采用Office2013红色的动画背景,允许用户自定义安装配置,参考如下组图: 1.Office2015的安装启动界面 2.Office2015的安装配置 3.Office20

如何免费安装微软Office 2013客户预览版

最近,微软发布了新一代Office--Office 2013客户预览版,包含:Word 2013.PowerPoint 2013.Excel 2013.OneNote和Outlook组件. Office 2013客户预览版可以像正常的Office一样使用,带来了更简洁的操作体验,更漂亮的文档模板和云存储文档的功能. 如果你想使用一款完全免费的最新版Office,这一版完全免费的Office 2013客户预览版绝对不容错过. 方法/步骤 1.在百度搜索"Office 2013客户预览版"