Swift之旅(四)对象和类

要定义一个类,只要在 class 后面加上类名即可。在类中定义属性的写法与定义常量和变量一样,只不过它是在类的范围里。同样,方法的定义和函数定义是一样的写法。

class Shape {
    var numberOfSides = 0
    func simpleDescription() -> String {
        return "A shape with \(numberOfSides) sides."
    }
}

试一试

用 let 增加一个常量属性,再加一个有一个参数的方法。

要创建类的实例,只需在类名后加上括号就可以了。用句点来访问类实例的属性和方法。

var shape = Shape()
shape.numberOfSides = 7
var shapeDescription = shape.simpleDescription()

这个版本的Shape类还差了点重要的东西:初始化器(博主注:其实就是构造函数),用来在类实例创建时构建该类。用 init 来表示。

class NamedShape {
    var numberOfSides: Int = 0
    var name: String

    init(name: String) {
        self.name = name
    }

    func simpleDescription() -> String {
        return "A shape with \(numberOfSides) sides."
    }
}

注意 self 是怎么用来把name参数传给name属性的。创建类实例时,参数就像调用函数时传参数那样传给初始化器。每个属性都需要指定一个值——不管是在定义时(就像numberOfSides)还是在初始化器里(就像name)。

如果要在对象被释放之前做一些清理工作,可以用 deinit 来创建一个析构函数。

要定义子类只需在类名后加分号,再写上父类的类名即可。Swift里并不要求类必须继承任何标准的父类,所以如果需要的话可以省略掉父类。

子类要重写父类的方法需要用 override 进行标记——如果没加override就重写了父类的方法是会被编译器报错的。编译器还会检测加了override的方法是不是真的是重写父类的方法。

class Square: NamedShape {
    var sideLength: Double

    init(sideLength: Double, name: String) {
        self.sideLength = sideLength
        super.init(name: name)
        numberOfSides = 4
    }

    func area() ->  Double {
        return sideLength * sideLength
    }

    override func simpleDescription() -> String {
        return "A square with sides of length \(sideLength)."
    }
}
let test = Square(sideLength: 5.2, name: "my test square")
test.area()
test.simpleDescription()

试一试

加一个NamedShape的子类Circle,有radius属性,并且在初始化器中接收该参数。在Circle类里实现一个area() 和 simpleDescription() 方法。

除了简单存储值外,属性还可以加getter和setter。

class EquilateralTriangle: NamedShape {
    var sideLength: Double = 0.0

    init(sideLength: Double, name: String) {
        self.sideLength = sideLength
        super.init(name: name)
        numberOfSides = 3
    }

    var perimeter: Double {
        get {
            return 3.0 * sideLength
        }
        set {
            sideLength = newValue / 3.0
        }
    }

    override func simpleDescription() -> String {
        return "An equilateral triangle with sides of length \(sideLength)."
    }
}
var triangle = EquilateralTriangle(sideLength: 3.1, name: "a triangle")
println(triangle.perimeter)
triangle.perimeter = 9.9
println(triangle.sideLength)

在周长的setter里,新的值有个被隐式的称为newValue的名字。你可以在set后面加个括号,显式地定义一个名字。

注意 EquilateralTriangle 类的初始化器有三步不同:

设置子类定义的属性值。

调用父类的初始化器。

更改父类定义的属性值。

其余要用到方法、getter或者setter的初始化工作也可以在这个时候进行。

如果不需要计算属性值但任然要在设置了新值之前或之后运行一段代码的话,就要用到 willSet 和 didSet。例如,下面的类确保了三角形的边长与正方形边长是一致的。

class TriangleAndSquare {
    var triangle: EquilateralTriangle {
        willSet {
            square.sideLength = newValue.sideLength
        }
    }
    var square: Square {
        willSet {
            triangle.sideLength = newValue.sideLength
        }
    }
    init(size: Double, name: String) {
        square = Square(sideLength: size, name: name)
        triangle = EquilateralTriangle(sideLength: size, name: name)
    }
}
var triangleAndSquare = TriangleAndSquare(size: 10, name: "another test shape")
println(triangleAndSquare.square.sideLength)
println(triangleAndSquare.triangle.sideLength)
triangleAndSquare.square = Square(sideLength: 50, name: "larger square")
println(triangleAndSquare.triangle.sideLength)

类里的方法与函数有一个很重要的不同。函数里的参数名只能用于函数内,但方法里的参数名还可以用在你调用该方法的时候(除了第一个参数)。默认情况下,方法调用时与方法自己内部,参数名是一样的。你可以再指定另一个名字,用于方法内。

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

遇到可选值的时候,你可以在方法、属性和下标等操作前写个 ?。如果 ?前的值是 nil ,那么 ? 后的所有东西都会被忽略,而且整个表达式的值是nil。否则,可选值被开启,?后的所有东西按照开启值来继续。不管哪种情况,整个表达式的值都是可选值。

let optionalSquare: Square? = Square(sideLength: 2.5, name: "optional square")
let sideLength = optionalSquare?.sideLength
时间: 2024-12-11 12:15:47

Swift之旅(四)对象和类的相关文章

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

原文:Swift中文教程(五)--对象和类 Class 类 在Swift中可以用class关键字后跟类名创建一个类.在类里,一个属性的声明写法同一个常量或变量的声明写法一样,除非这个属性是在类的上下文里面,否则,方法和函数的写法也是这样: 1 class Shape { 2 var numberOfSides = 0 3 func simpleDescription() -> String { 4 return "A shape with \(numberOfSides) sides.&q

Swift学习——A Swift Tour 对象和类

Objects and Classes  对象和类 使用关键字 class 定义一个类,在定义类的属性的时候与常量或者变量的定义相同(继承父类的属性定义不同),方法和函数的定义也相同 class Shape { var numberOfSides = 0 func simpleDescription() -> String { return "A shape with \(numberOfSides) sides." } } 使用 ()来声明类的实例,使用点 . 语法来获取类的属

Java笔记十四.深入理解类和对象(1)

Java是一种完全面向对象的编程语言(C是面向过程).所谓面向对象编程(OOP),即是一种编程风格,它通过给程序中加入扩展语句,把函数"封装"进编程所必需的"对象"中.OOP 达到了软件工程的三个主要目标:重用性.灵活性和扩展性.其实,面向对象就是把一切东西看成一个个对象,比如人,车,面包,等等,然后把这些对象拥有的属性变量,比如年龄,民族,工作地点,变质期,寿命,还有操作这些属性变量的函数(方法)打包成一个类来表示,这个类的一个抽象就是一个对象.在Java程序中,

《JVM》(四)Class类文件结构,对象的创建

Class类文件结构 class文件是一组以8字节为单位的二进制流,只有两种数据类型:无符号数(基本数据类型),表(复合数据类型) 魔数 版本号 常量池(占class空间最大的数据之一,从1开始计数) 1.字面量 :接近于java层面的常量概念,如字符串,声明为final的常量 2.符号引用:类和接口的全限定名,字段和方法的描述符 字段描述符:描述字段数据类型 方法描述符:描述方法参数列表和返回值 访问标志 类索引,父类索引,接口索引集合 字段表集合(描述接口或类中声名的变量,不包括方法中的局部

[Swift通天遁地]四、网络和线程-(13)创建一个Socket客户端

请点击Socket服务端文章:[Swift通天遁地]四.网络和线程-(14)创建一个Socket服务端 本文将演示Socket(套接字)客户端的使用. 网络上的两个程序通过一个双向的通信连接实现数据的交换,这个连接的一端称为一个socket. 在Github中下载项目:[SwiftSocket] 在[Source]文件夹,按下[Shift]选择多个文件. [yudpsocket.c] [ytcpsocket.c] [UDPClient.swift] [TCPClient.swift] [Swif

对象和类

对象和类 一.对象的特征 1.属性--对象具有各种特征 2.每个对象的每个属性都有特定值 3.方法--对象执行的操作 4.对象:用来描述客观事物的一个实体,由一组属性和方法构成 二..类 类是模子,定义对象将会拥有的特征(属性)和行为(方法) 类是对象的类型--不同于int类型:具有方法 三.类和对象的关系   类是抽象的概念,仅仅是模板   对象是一个看得见摸得着的具体实体 四.如何创建对象和使用对象 使用对象的步骤 a.创建对象 类名  对象名=new 类名(): b.引用对象成员:使用".

Swift学习 (四)

5.枚举与结构体: 不必给枚举成员提供一个值.如果我们想要为枚举成员提供一个值(raw value),我们可以用字符串,字符,整型或浮点数类型. 1 2 3 4 5 6 7 enum CompassPoint { case North case South case East case West   }   var directionToHead = CompassPoint.West 结构体 Struct在Swift中和类有许多相同的地方,可以定义属性,方法,初始化方法,可通过extensio

一大波Java来袭(四)String类、StringBuilder类、StringBuffer类对比

本文主要介绍String类.StringBuffer类.StringBuilder类的区别  : 一.概述 (一)String 字符串常量,但是它具有不可变性,就是一旦创建,对它进行的任何修改操作都会创建一个新的字符串对象. (二)StringBuffer 字符串可变量,是线程安全的,和StringBuilder类提供的方法完全相同. 区别在于StringBuffer每个方法中前面添加了"synchronized",保证其是线程安全的. (三)StringBuilder 字符串可变量,

JavaScript学习总结(十四)——JavaScript编写类的扩展方法

在?J?a?v?a?S?c?r?i?p?t?中?可以使?用?类的p?r?o?t?o?t?y?p?e属性来?扩?展?类的属?性?和?方?法,在实际开发当中,当JavaScript内置的那些类所提供的动态方法和动态属性不满足我们实际开发时,我们就可以通过"prototype"属性给自定义类添加方法和属性或者扩展原有的类中的方法和属性. 一.扩展JavaScript内置类,添加动态方法 语法格式: 类名.prototype.方法名 = function([param1],[param2],.

Swift中文教程(四)--函数与闭包

原文:Swift中文教程(四)--函数与闭包 Function 函数 Swift使用func关键字来声明变量,函数通过函数名加小括号内的参数列表来调用.使用->来区分参数名和返回值的类型: 1 func greet(name: String, day: String) -> String { 2 return "Hello \(name), today is \(day)." 3 } 4 greet("Bob", "Tuesday")