原文:Swift中文教程(五)--对象和类

  

  Class 类

  在Swift中可以用class关键字后跟类名创建一个类。在类里,一个属性的声明写法同一个常量或变量的声明写法一样,除非这个属性是在类的上下文里面,否则,方法和函数的写法也是这样:

1 class Shape {
2     var numberOfSides = 0
3     func simpleDescription() -> String {
4         return "A shape with \(numberOfSides) sides."
5     }
6 }

练习:

用let关键字添加一个常量属性,添加另一个方法用来接收参数。

  在类名后面加小括号来创建类的实例化,使用.(点号连接符)来访问实例的方法和属性:

1 var shape = Shape()
2 shape.numberOfSides = 7
3 var shapeDescription = shape.simpleDescription()

  这个版本的Shape类缺少一个重要的东西:构造器--类被创建后的设置。可以使用init来创建一个:

 1 class NamedShape {
 2     var numberOfSides: Int = 0
 3     var name: String
 4
 5     init(name: String) {
 6         self.name = name
 7     }
 8
 9     func simpleDescription() -> String {
10         return "A shape with \(numberOfSides) sides."
11     }
12 }

  注意,此处的self是用来区分构造器内的name参数和name属性的。创建类的实例时,构造器里的参数传递和函数的参数传递形式是一样的。每个属性都需要为其指定一个值,无论是在声明中(如nameOfSides),或是在构造器内(如name)。

  使用 deinit 来创建一个析构器,来执行对象销毁时的清理工作。

  继承和多态

  子类可以加冒号后直接跟超类名,子类声明时并不需要非得制定任何标准基类,所以子类后的超类可以被忽略。

  子类的方法覆盖或重载超类中的实现要加上override标记,否则,编译器会报错,编译器也会检测被标记为override的重载方法到底有没有覆盖到超类。

 1 class Square: NamedShape {//接上一例,NamedShape为超类
 2     var sideLength: Double
 3
 4     init(sideLength: Double, name: String) {
 5         self.sideLength = sideLength
 6         super.init(name: name)
 7         numberOfSides = 4
 8     }
 9
10     func area() ->  Double {
11         return sideLength * sideLength
12     }
13
14     override func simpleDescription() -> String {//在此处用override重载了上一例中超类NameSpace的方法simpleDescription
15         return "A square with sides of length \(sideLength)."
16     }
17 }
18 let test = Square(sideLength: 5.2, name: "my test square")
19 test.area()
20 test.simpleDescription()

练习:

编写另一个NamedShape的子类:Circle ,传入半径和名字作为参数到其构造器,并在Circle类中实现area和describe方法。

  此外,声明过的属性通常还有一个get和一个set方法:

 1 class EquilateralTriangle: NamedShape {
 2     var sideLength: Double = 0.0
 3
 4     init(sideLength: Double, name: String) {
 5         self.sideLength = sideLength
 6         super.init(name: name)
 7         numberOfSides = 3
 8     }
 9
10     var perimeter: Double {
11     get {
12         return 3.0 * sideLength
13     }
14     set {
15         sideLength = newValue / 3.0
16     }
17     }
18
19     override func simpleDescription() -> String {
20         return "An equilateral triagle with sides of length \(sideLength)."
21     }
22 }
23 var triangle = EquilateralTriangle(sideLength: 3.1, name: "a triangle")
24 triangle.perimeter
25 triangle.perimeter = 9.9
26 triangle.sideLength

  

  上例中,perimeter的set中值的默认名是newValue,你可以再set后面以小括号的方式为其指定其它的名字。

  请注意, EquilateralTriangle类的构造器有三个不同的步骤:

    第一步,设置子类各个属性的值;

    第二步,调用超类的构造器;

    第三步,改变超类中定义的属性的值,其它的方法,get,set等都可以在此一步骤实行。

  如果你不需要计算属性的值,但是想在设置属性值之前或之后执行代码,那么你可以使用willset(之前)和didset(之后)。如下例中的类--确保三角形的边长始终与矩形边长相等:

 1 class TriangleAndSquare {
 2     var triangle: EquilateralTriangle {
 3     willSet {
 4         square.sideLength = newValue.sideLength
 5     }
 6     }
 7     var square: Square {
 8     willSet {
 9         triangle.sideLength = newValue.sideLength
10     }
11     }
12     init(size: Double, name: String) {
13         square = Square(sideLength: size, name: name)
14         triangle = EquilateralTriangle(sideLength: size, name: name)
15     }
16 }
17 var triangleAndSquare = TriangleAndSquare(size: 10, name: "another test shape")
18 triangleAndSquare.square.sideLength
19 triangleAndSquare.triangle.sideLength
20 triangleAndSquare.square = Square(sideLength: 50, name: "larger square")
21 triangleAndSquare.triangle.sideLength

  类的方法与函数有一个重要的区别:函数的参数名仅作用于此函数内,而方法的参数名可以用于调用方法(第一个参数除外)。缺省时,一个方法有一个同名的参数,调用时就是方法本身。你可以指定第二个名字,在方法内部使用:

1 class Counter {
2     var count: Int = 0
3     func incrementBy(amount: Int, numberOfTimes times: Int) {
4         count += amount * times
5     }
6 }
7 var counter = Counter()
8 counter.incrementBy(2, numberOfTimes: 7)

  当与可选值(详见第三章的If语句介绍)一起工作时,你可以在方法或属性前写 "?" 操作符。如果值在"?"之前就已经是 nil ,所有在 "?" 之后的都会自动忽略,而整个表达式是 nil 。另外,可选值是未封装的,所有 "?" 之后的都作为未封装的值。在这两种情况中,整个表达式的值是可选值:

1 let optionalSquare: Square? = Square(sideLength: 2.5, name: "optional square")//?可选值的介绍详见第三章的If语句部分
2 let sideLength = optionalSquare?.sideLength

谢谢,Swifter-QQ群:362232993,同好者进~

github地址:https://github.com/Joejo/Swift-lesson-for-chinese

  

Swift中文教程(五)--对象和类相关推荐

  1. Swift中文教程(九) 类与结构

    类与结构是编程人员在代码中会经常用到的代码块.在类与结构中可以像定义常量,变量和函数一样,定义相关的属性和方法以此来实现各种功能. 和其它的编程语言不太相同的是,Swift不需要单独创建接口或者实现文 ...

  2. Swift中文教程(三)--流程控制

    Swift中文教程(三)--流程控制 原文:Swift中文教程(三)--流程控制 Swift用if和switch编写条件控制语句,用for-in,for,while和do-while编写循环.条件控制 ...

  3. python 类和对象 经常用吗_python基础教程之对象和类的实际运用

    我们熟悉了对象和类的基本概念.我们将进一步拓展,以便能实际运用对象和类. 调用类的其它信息 中提到,在定义方法时,必须有self这一参数.这个参数表示某个对象.对象拥有类的所有性质,那么我们可以通过s ...

  4. Swift中文教程(二十二) 泛型

    泛型代码可以让你写出根据自我需求定义.适用于任何类型的,灵活且可重用的函数和类型.它的可以让你避免重复的代码,用一种清晰和抽象的方式来表达代码的意图. 泛型是 Swift 强大特征中的其中一个,许多 ...

  5. 苹果Swift语言中文教程(九) 类与结构

    类与结构是编程人员在代码中会经常用到的代码块.在类与结构中可以像定义常量,变量和函数一样,定义相关的属性和方法以此来实现各种功能. 和其它的编程语言不太相同的是,Swift不需要单独创建接口或者实现文 ...

  6. Swift中文教程(十五) 析构

    在一个类的实例被释放之前,析构函数会被调用.用关键字deinit来定义析构函数,类似于初始化函数用init来定义.析构函数只适用于class类型. 1.析构过程原理 Swift 会自动释放不再需要的实 ...

  7. Swift中文教程(五)控制流

    Swift提供了所有C语言中相似的控制流结构.包括for和while循环:if和switch条件语句:break和continue跳转语句等. Swift还加入了for-in循环语句,让编程人员可以在 ...

  8. Swift中文教程(二十三) 高级运算符

    除了基本操作符中所讲的运算符,Swift还有许多复杂的高级运算符,包括了C语和Objective-C中的位运算符和移位运算. 不同于C语言中的数值计算,Swift的数值计算默认是不可溢出的.溢出行为会 ...

  9. Swift中文教程(十八) 类型检查

    类型检查是一种检查类实例的方式,并且或者也是让实例作为它的父类或者子类的一种方式. 类型检查在 Swift 中使用is 和 as操作符实现.这两个操作符提供了一种简单达意的方式去检查值的类型或者转换它 ...

最新文章

  1. Hibernate双向多对多关联
  2. Qt Creator分析代码
  3. 前端学习(2846):css浮动和定位布局
  4. 如何把Linux工具里的“军刀”BusyBox移植到RT-Thread Smart?
  5. java什么是类和对象,Java类和对象的概念
  6. Python《突破JS动态加载,成功爬取漫画》
  7. Okhttp使用简析——Android网络请求框架(一)
  8. Java的native方法-----你必须要知道的JAVA知识
  9. 矩池云使用conda安装离线安装包
  10. jieba分词怎么操作_常用分词工具使用教程
  11. 装双系统出现winload.efi,也就是安装win10,提示0xc0000359
  12. AMI编码规则与HDB3编码规则详解
  13. 一篇文章教你如何刷Letcode进大厂
  14. protoc ——protubuf编译后的可执行文件命令usage
  15. VS下载插件慢的解决方法。
  16. 【漏洞复现】Hadoop YARN 资源管理系统 REST API未授权访问
  17. 使用 JDBC 进行 MySQL 编程
  18. JNDI(Java Naming and Directory Interface)介绍
  19. uniApp App端跳转到深色页面闪白记录及优化处理方法
  20. 关于echart 饼图显示不出来 挖坑总结

热门文章

  1. 人工智能的圣杯:关于可解释AI(XAI)的一切
  2. 盘点丨那些顶级的AI机器人“大脑”
  3. 重磅丨人工智能三年国家战略公布:8大领域要火!
  4. (深入理解)matplotlib的交互模式(block,interactive,ion,ioff,draw,show,plot等的区别)
  5. Pytorch+CNN+MNIST手写数字识别实战
  6. 一幅图读懂量子力学(数学的判决)
  7. 关上Deepfake的潘多拉魔盒,RealAI推出深度伪造视频检测工具
  8. Nature好文:过去150年,科学与产业经历四段情缘!
  9. 力拎30磅!波士顿动力物流机器人Handle亮相,还会摆货架
  10. 物联网可应用于十大行业嘛?