Swift之类与结构体

//: Playground - noun: a place where people can play


import UIKit


var str = "类与结构体"

/*结构体

 OC中结构体只可以定义属性而不能定义方法。而在Swift中,结构体和类十分相似,其中既可以定义属性也可以定义方法,但其不像类一样具有继承的特性。

 使用struct来定义结构体,结构体中可以声明变量或常量作为结构体的属性,也可以创建函数作为结构体的方法,结构体使用点语法来调用其中的属性和方法。

 */

//定义一个car

struct Car{

//    设置属性-价格和品牌

    var price:Int

    var brand:String

    var petrol:Int //耗油量

//    定义一个行路的方法

    mutating func drave(){

        if petrol>0 {

            petrol -= 10

            print("耗费了10升油")

        }


    }

    //        定义一个加油的方法

   mutating func addPetrol(){

        petrol += 10

        print("加了10升油")

    }

}

var car = Car(price: 1000000, brand: "宝马", petrol: 50)

print("这是一辆\(car.brand),汽车价格是\(car.price),油量\(car.petrol)")

car.drave()

print("剩余\(car.petrol)升")

//注意,Swift语言中的数据类型分为值类型和引用类型,结构体、枚举等其他除类之外的所有数据类型都属于值类型,只有类是引用类型的。值类型和引用类型的最大区别在于当进行数据传递时,值类型总是被复制,而引用类型不会被复制,引用类型是通过引用计数来管理其生命周期的。

/*

 类

 类是较结构体更加高级的一种数据类型。简单的理解,类是编程世界中万物的抽象,使用类可以模拟万物的对象。Swift语言中使用class来声明类。

 */

class CarClass{

    var price:Int

    var brand : String

    var petrol: Int

//

    func drave() {

        if petrol>0 {

            petrol -= 1

        }

    }

    func addPetrol() {

        petrol += 1

    }

    init(price:Int,brand:String,petrol:Int) {

        self.price = price

        self.brand = brand

        self.petrol = petrol

    }

}

//由此可以看出,类和结构体创建属性和方法的代码基本一样。不同的是,结构体不需要提供构造方法,会自动根据属性生成一个构造方法;类则要求提供构造方法,在init()工作方法中,完成对类中所有属性的赋值操作


var car1 = CarClass(price: 1000000, brand: "奔驰", petrol: 100)

print(car1.price)

var car2 = car1//1000000

car2.price = 999999

print(car1.price)//999999

print(car2.price)//999999

//由上面的代码可以看出如果将类的实例,传递给一个新的变量,那么修改新的变量会影响原始变量。

/*

 继承

 继承是类独有的特点,子类和父类通过继承关系进行关联,并且子类可以对父类进行扩展。Swift语言中,不继承任何类的类称为基类,继承而来的类称为子类。在编程中,子类会继承父类的属性和方法,子类也可以定义自己的属性和方法。

 */

//创建一个交通的工具基类

class Transportation {

    var petrol : Int

    func drave()  {

//        具体有子类实现

        if petrol == 0 {

            self.addPetrol()

        }

        print("父类drave方法")

    }

    func addPetrol()  {

        petrol += 10

    }

    init(petrol: Int) {

        self.petrol = petrol

    }

}

//创建一个船类,继承Transportation

class Boat: Transportation{

//自己的属性

    var floor:Int

    

//    重写父类方法

    override func drave() {

        super.drave()

        print("海上航行了50km")

        self.petrol -= 2

    }

/*

   init(floorCount :Int) {

         floor = floorCount

     }

     会报错

     “Super.init isn't called on all paths before returning from initializer”

     在子类的构造器中,父类的成员变量必须通过父类的designated initializer进行初始化。也就是说,我们必须调用super.init,而且在调用super.init之前不能使用和访问任何父类的成员变量,否则“use of 'self' in property access 'name' before super.init initializes self”

     

  */


    init(floor:Int,petrol:Int) {

        self.floor = floor

        super.init(petrol: petrol)

    }

}

//创建一个飞机类

class Airplane:Transportation{

    var height:Float

    init(height:Float,petrol:Int) {

        self.height = height

        super.init(petrol: petrol)

    }

    override func drave() {

        super.drave()

        print("在天上飞行可1000km")

        self.petrol -= 2

    }

}

//创建船实例,飞机实例

var boat = Boat(floor: 5, petrol: 30)

var airplane = Airplane(height: 10000, petrol: 20)

//调用drave()方法

boat.drave()

airplane.drave()

//注意,Swift语言中还提供了一个final关键字,final关键字用于修饰某些终极的属性、方法或者类。被final修的属性和方法不能被子类继承

/*类和结构体的作用十分相似,但是两者有着本质的不同,他们在数据传递的机制不同,分别适用于不同的应用场景

 下面的几种情况下建议使用结构体:

     a.要描述的数据类型其中只有少量的简单数据类型的属性

     b.要描述的数据类型在数据传递时需要以复制的方式进行

     c.要描述的数据类型中的所有属性在进行传递时需要以复制的方式进行

     d.不需要继承另一个数据类型

 关于值类型和引用类型,应该注意,如果对值类型进行比较操作,应使用等于运算符“==”;对引用类型进行比较,应使用等同运算符“===”

其实在Swift语言中,Array、String、Dictionary、Set这些数据都是采用结构体来实现的,因此在Swift语言中,Array、String、Dictionary、Set在数据传递时总是被复制。但是在苹果的官方文档有介绍:在开发者的代码中,看似复制行为总会发生。然而,Swift语言在幕后会控制只有绝对需要时才会进行真正的复制操作,以确保性能最优,因此在实际开发中没必要回避复制行为来确保性能。

 */

//练习

//1、设计一个学生类,为每个学生设计姓名、性别和年龄属性,并提供一个学习的方法

enum Sex{

    case

    case

}

class Student{

    let name: String

    let sex: Sex

    let age: Int

    init(name:String,sex:Sex,age:Int) {

        self.name = name

        self.sex = sex

        self.age = age

    }

//    学习的方法

    func study() {

        print("\(self.name)在学习,性别:\(self.sex),年龄:\(self.age)")

    }

}

//创建实例

var student = Student(name: "张三", sex: ., age: 18)

student.study()


//2、结合上面的学生类,设计一个班级类,其中需要有班级名、学生人数和班长3个属性,并设计转入和转出学生的方法。

class ClassStu{

    var name: String

    var numCount : Int//人数

    var monitor :Student

    init(name:String,numCount:Int,monitor:Student) {

        self.name = name

        self.numCount = numCount

        self.monitor = monitor

    }

    func addStudent()  {

        

        numCount += 1

        print("转入了一个学生,现在一共\(self.numCount)名学生")

    }

    func deleStudent()  {

        

        numCount -= 1

        print("转出了一名学生,现在一共\(self.numCount)名学生")

    }

//    描述方法

    func description()  {

        print("\(self.name),共有\(self.numCount)名学生,班长是\(self.monitor.name)")

    }

}

//创建一个班长

var monitor = Student(name: "莉莉", sex: ., age: 19 )

//创建一个班级

var class1 = ClassStu(name: "二年级一班", numCount: 35, monitor: monitor)

class1.addStudent()

class1.description()


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值