Swift 基础语法 <与 OC作对比>

来源:互联网 发布:生态文明我知我行答案 编辑:程序博客网 时间:2024/05/16 02:10

Swift 基础语法 <与 OC作对比>

你能看这篇文章表明你对OC语言已具备一定基础了,那下面我编写将比对着OC进行,这张图是打开编写工具Xcode的标准

print("Hello, World!")/*/*println("fuck")*/println("李震,操你妹!")*///Swift//1.是一门开发语言.用于开发iOS 及 OS x应用//2.是基于cocoa 及 cocoa Touch 框架//3.集合了C及Object-C的优点, 且不受C的兼容性限制//4.相对于object - C 书写习惯上有了不小的改变/**********常量 变量 分号 输出语句***********///peint 输入不换行,println输出换行print("不换行", terminator: "")print("换行")//let 用于声明一个常量,只可以被赋值一次,不能改变let year = 2015print(year)//只输出常量或变量,直接跟常量名变量名//var 用于声明一个变量var age = 20age = 21print(age)//常量或变量的命名规范    //1.可以使用出了数字符号,制表符,箭头,保留字外 其他所有的Unicode字符,不能以数字开头var 黑哥哥 = 18var �� = "老牛哥"var 草泥马 = 21print(黑哥哥)print("\(��) \(黑哥哥)")//swift中一般语句的结尾不再用分号, 但是当一个定义多个常量或变量是,需要分号来间隔var 姓名 = "黑哥哥", 外貌 = "帅气"; var 年龄 = "18"print("\(姓名)外貌很\(外貌)")//函数方法名也可以写成中文的,或者Unicode图片func 输出(){    print("你是我的小呀小苹果")}输出()/**********常量和变量的类型************///整型:根据操作系统自动辨识,在64位下, Int = Int64 根据范围可分为Int8, Int16, Int32, Int64var number = 45number = -20print(number)//浮点型:Float / Double//swift中存在类型推断机制,会把下面变量score推断为Double类型var score = 45.9score = 100.12print(score)//类型推断机制//声明常量或是变量的时候, 我们不需要显式(看得见的方式)指定变量的类型, 类型推断机制会根据所赋值的类型推断变量的类型(注意:Float/Double)//类型安全机制 : 当我们把一个变量的类型声明成Int型时,我们就不会把string类型的赋值给它,类型安全机制会检测两者的类型是否匹配//数值型字面量:let tenValue = 39 //十进制字面量表达let twoValue = 0b11010//二进制let eightValue = 0o32//八进制let sixteenValue = 0x1A //十六进制var count = 67//结合元组进行输出print("\(tenValue) \(twoValue) \(eightValue) \(sixteenValue)")print(tenValue, twoValue, eightValue, sixteenValue)//数值型字面量的转化var changeValue1:Int8 = 100var changeValue2:Int64 = 200//Int64(changeValue1):将Int8 转成 Int64, 否则报类型错误var sum = Int64(changeValue1) + changeValue2;print(sum)var key1:Float = 12.0var key2:Double = 18.00var sum1 = Double(key1) + key2print(sum1)//类型别名typealias HEHE = Intvar length:HEHE = 34print(length)//BOOL 类型:和C语言中的差别Lswift中Bool类型的值只有true 和false   而C中,有YES和NO. 而且还有 0和非0var isMan:Bool = falsevar isFineDay = truevar 李春是一个强壮的男人 = trueprint(李春是一个强壮的男人)//bool类型输出结果是true / falseif 李春是一个强壮的男人{    print("怎么可能")}//swift中新的类型//1.元组:多个任意类型的值组合而成一个元组var requestResult = (200, "未注册用户")print(requestResult)//输出整个元组print(requestResult.0)//输出元组中相应下标位元素print(requestResult.1)//var birthday:(String, Int, String, Bool) = ("2015", 10, "20", true)var yearString = birthday.0print(yearString)//给元组添加描述var httpCode = ("100", 34, codeValue:404, desxription:"error")//获取描述元组元素print(httpCode.0)print(httpCode.1)//获取元组描述print(httpCode.codeValue)print(httpCode.desxription)//断言:本省并没有什么用,只是为了方便开发人员调试bug,结合一个表达式来用var stopValue = 4//当stopValue > 0 表达式为true时, 对程序没有任何影响,当未符合条件时,程序终止,便于开发阶段的调试assert(stopValue > 0, "stopValue值必须大于零")//运算符 之 一元运算符//负号运算符,对原值取负var fuHaoNumber1 = -89var fuHaoNumber2 = -fuHaoNumber1print(fuHaoNumber2)//加号运算符var number1 = 35var number2 = 65var number3 = number1 + number2number1 += number3print(number3)print(number1)//取余运算符var yuResult = 10 % 3print(yuResult)//比较表达式var a = 1var b = 4var aAndb = a > bprint(aAndb)//自增自减运算符:++, --var zizeng = 5var zijian = 5zizeng++zijian--print(zizeng)print(zijian)//逻辑运算符:&&(与), ||(或), !(非)var c = 1, d = 2, e = 3if c < d && d < e {    print("OK")}else {    print("Fuck")}if (c < d || d < e) && d != 2  {    print("OK")}else {    print("Fuck")}//swift 新增运算符//区间运算符: ...(全闭区间), ..(前闭后开区间)//区间运算符一般结合for.....in 使用for numberA in 1...6 {    print(numberA)}for numberB in 2..<4 {    print(numberB)}//字符串var stringValue = "移动班\t傻逼们\n"print(stringValue)//转义字符var stringValue1 = "移动班\"逗比们\""print(stringValue1)//格式输出字符串var classNum = 34var className = "南阳理工"print("\(className)\(classNum)班")var newString = "来自\(className)的\(classNum)班"print(newString)//1.swift 中自带的字符串没有可变和不可变之分,是否可变取决于let 或 var//2.swift 中可以使用OC中的字符串,并且也推荐使用OC中的字符串进行复杂操作//3.swift 中自带的字符串是值类型var str1 = "cangLaoShi"var str2 = str1str2 += "HH"print(str1)print(str2)var ocStr0 = NSMutableString(string: "laoFan")var ocstr1 = ocStr0//OC中的拼接方式ocstr1.appendString("is a girl")print(ocstr1)//字符串截取var cutStr = "qwertyuiop"var index = cutStr.stringByPaddingToLength(5, withString: cutStr, startingAtIndex: 0)print(index)/*swift2.0截取方法//var index = cutStr.startIndex.advancedBy(4)//var subStr = cutStr.substringToIndex(index)*///推荐使用var cutString = NSMutableString(string: "123456789")var sutString = cutString.substringToIndex(5)print(sutString)//数组:swift中的数组没有变和不变之分,取决于 let 或是 varvar swiftArray = ["gengShen", 25, 78.5, true]print("siwftArray = \(swiftArray)")var ocArray = NSMutableArray(array: swiftArray)print(ocArray)var ocArray1 = NSArray(array: swiftArray)print(ocArray1)//增//1.swift数组元素的添加swiftArray += ["pan girl", "nice boy"]print(swiftArray)//2.siwft数组的插入swiftArray.insert("Fuck you", atIndex: 0)print(swiftArray)//OC数组的添加元素ocArray.addObject("see you")print(ocArray)ocArray.insertObject("人之初,性冷淡", atIndex: 0)print(ocArray)ocArray.addObject(23)ocArray.addObject(23)print(ocArray)////删除,oc数组//ocArray.removeObject(23)//println(ocArray)////ocArray.removeObjectAtIndex(0)//println(ocArray)////ocArray.removeAllObjects()//println(ocArray)//改//swift 中更改数组元素print("\n---------更改元素-----------\n")swiftArray[0] = "111111111"print(swiftArray)swiftArray[0] = 78print(swiftArray)//根据区间替换元素,超出的追加进数组swiftArray[0...2] = [1, 2, 3, 4, 5]print(swiftArray)//重置数组//swiftArray = [1, 2]//println(swiftArray)//OC数组更改元素print("-------------------------")ocArray.replaceObjectAtIndex(0, withObject: "biaobiao")print(ocArray)//查//swift 数组查询//for...in 时不需要写参数(value)类型for value in swiftArray {    print("swift value = \(value)")}//使用全局enumerate()函数返回一个由数组下标和对应值组成的元组//for (index, value) in swiftArray.enumerate()//{//    print("index = \(index), value = \(value)")//}//OC中的数组查询for value in ocArray {    print("ocArray = \(value)")}for var i = 0; i < ocArray.count; i++ {    print("ocArray[\(i)] = \(ocArray[i])")}//OC中数组的初始化//当我们声明成NSArray时, 即便前面是var,仍然不能插入数据,因为OC中的数组能不能被插入数据取决于本身的类型,而不是前面的var 或者 let 关键字var initSwiftArray = NSArray()//不可变var initSwiftArray1 = NSMutableArray()//可变initSwiftArray1.addObject("df")/**********字典*******************///swift中的字典var swiftDic = [    "name":"honghong",    "age":24,    "sex":"男",    "hobby":"beautiful girl"]print(swiftDic)//OC中的字典var ocDic = NSMutableDictionary (dictionary: swiftDic)print(ocDic)//字典 增//swift字典增加swiftDic ["sex"] = "女"//如果键存在,则改值swiftDic ["sonCount"] = 24//如果键不在,则添加键值对print(swiftDic)//OC字典的增ocDic.setObject("zhaoritain", forKey: "wifi")print(ocDic)//swift 字典的 删swiftDic.removeValueForKey("sonCount")print(swiftDic)//OC 字典 删ocDic.removeObjectForKey("wifi")print(ocDic)//swift 字典 改//当调用字典的updateValue方法时,如归key值存在,就替换对应的老值, 并返回老值var result = swiftDic.updateValue(18, forKey: "age")print("result = \(result), \(swiftDic)")//当调用字典的updateValue方法时,如归key值不存在,就添加键值对, 并返回nilvar result1 = swiftDic.updateValue(1, forKey: "fatherCount")print("result1 = \(result1), \(swiftDic)")//OC 字典 改//如果key在则替换,如果不在则添加ocDic.setValue("34", forKey: "class")print(ocDic)//swift字典的 查//遍历字典得到 包含key值和value值的元组for (key, value) in swiftDic {    print("key = \(key), value = \(value)")}//OC 字典的 查//遍历字典得到 包含key值和value值的元组for (key, value) in ocDic {    print("key = \(key), value = \(value)")}print("----------- ------------>swift可选类型<--------------- -----------")//swift  中的 可选类型<? !>(新类型)//var personName:String?  代表了这个变量是个可选类型,可以先不对其进行赋值,如果在取值时仍没有赋值,则结果为nil<nil为值类型, 区别于OC中的空指针nil,这里的nil是一个确切的值>,打印时不需要加叹号,如果赋过值,就需要在取值时后面跟叹号进行解包取值(强制解析)//当我们给可选类型赋值后,在后面再次取这个值时,需要在变量的后面跟上叹号<!>var personName:String?personName = "honghong"print(personName!)//可选类型隐式解析(告诉系统可选类型一定有值)//声明成隐形解析,它也是可选类型,只不过方便我们调用,不需要我们在使用时进行强制解析var studentScore:Float!studentScore = 45.3print(studentScore)//空合运算符(??)//1.空合运算符都是结合可选类型使用,如果是使用非可选类型,那么空合运算符(??)后面的将会被短路//2.先判断运算符前面部分是否有值,如果空,则取后面的值,如果不为空,则先对其强制解析,取出其值var aValue:Int?aValue = 9var khValue = aValue ?? 29print(khValue)//三目运算符var result10 = false ? 1 : 2print(result10)print("Hello, World!")/***********控制流**************///if 语句var aggCount:Int = 230if aggCount < 210{    print("小鸡,接着下")}else {    print("你可以歇息一下")}//if...else 语句支持可选类型的值绑定, 当可选类型值不为nil时, 会将其强制解析,赋值给局部变量,就可以在分支中使用次局部变量,当为nil时则执行else分支var orangeCount:Int? = 3if var count = orangeCount {    print("count = \(count)")}else {    print("可选类型的值为空")}//for ... in 直接写参数,不需要类型for value in 1...6 {    print("value = \(value)")}//不需要使用区间内的值时可以不写,用_替代for _ in 1...5 {    print("123221231232")}//for 循环for var i = 0; i < 10; i++ {    print("i = \(i)");}// while 循环 var whileIndex = 0while whileIndex < 20 {    print("whileIndex = \(whileIndex)")    whileIndex++}//do...while 循环:2.0后 do...while 变 repeat..whilevar doWhileIndex = 0repeat{    print("doWhileIndex = \(doWhileIndex)")doWhileIndex++}while doWhileIndex < 20//switch .. case 语句//1.OC中case后面不跟break会执行这个case后执行下一个case,直到break出现或执行完<贯穿>//2.在swift中case后面是否加break没有影响//3.在swift中,如果想要实现贯穿,就去掉break加上fallthrough//4.当某个case后面没有要执行的语句时,就加break//5.在swift中, 必须添加 default分支//6.当一个case 要表示一个区间时可以使用case1...10 : 此种写法var switchValue = 9switch switchValue {case 2 : print("10")    breakcase 1: print("9")    breakcase 0 : print("8")    breakdefault : print("other number")}//贯穿var switchValue1 = 10switch switchValue1 {case 3 : print("10")    fallthroughcase 2 : print("9")    fallthroughcase 1 : print("8")    fallthroughdefault : print("other number")}var switchValue2 = 9switch switchValue2 {case 1...10 : print("10")    breakcase 11...20: print("9")    breakcase 0 : print("8")    breakdefault : print("other number")}print("\n*********************switch语句的值绑定************************\n")//swift switch语句的值绑定//当条件满足时会把值自动的赋给我们声明的局部变量或常量,就可以在case语句中,使用该局部变量var (a, b) = (10, 10)switch (a, b) {case (let x, 0):    print("\(x), 0")case (0, let y):    print("0, \(y)")default:    print("other")}//标签语句//多用于循环嵌套, 当我们想要根据某个条件结束指定循环时,就该给指定循环加一个标签, 用于标识, 识别它hou:while true {    for var i = 0; i < 10; i++ {        print("i = \(i)")//        break 结束本个//        continue 结束本次        if i == 9 {            //根据标签,结束指定循环            break hou        }    }}/*******************函数*********************/print("********************函数************************")//函数: 格式: func 函数名(参数列表)  返回值//无返回值无参数,没有返回值时可以不写 或 ->void 或 ->()func sayHello(){    print("Hello World")}func sayHello1()->Void{    print("Hello World")}func sayHello2()->(){    print("Hello World")}//函数调用sayHello()sayHello1()sayHello2()//有参数(参数类型必须有)无返回值func printString(str:String) {    print(str)}printString("jjfly")//无参数有返回值(->返回值类型)func returnClassNumber()->String {    return "34"}var classNumber = returnClassNumber()print(classNumber)//有参数,有返回值//单个返回值func returnMaxNumber(num1:Int, num2:Int)-> Int {    return num1 > num2 ? num1 : num2}//2.0 之后有异常var result = returnMaxNumber(10, num2: 20)print(result)//多个返回值//当一个函数,想要返回多个值时,可以使用元组进行返回func returnMaxNumber1(num1:Int, num2:Int)-> (Int, Int) {    return num1 > num2 ? (num1, num2) : (num2, num1)}var result1 = returnMaxNumber1(10, num2: 20)print(result1)//函数中形参默认为let 如果想再参数中对其修改,就在形参名前加 varfunc print10BeiNumber(var num:Int) {    num = num * 10    print("num = \(num)")}print10BeiNumber(20)//完成两数交换//想在函数内部完成对实参的值交换,就需要使用inout(输入输出关键字)来修饰形参, 并且在调用函数时, 对实参进行取址操作func swipNumber(inout num1:Int, inout num2:Int) {    var temp = 0    temp = num1    num1 = num2    num2 = temp}var m = 12var nn = 20swipNumber(&m, num2: &nn)print("m = \(m), nn = \(nn)")//定义函数的外部参数名//2.0之后多参情况下会有形参名提醒,不用在加 #func eatFood(foodType foodType:String, foodPrice:Float) {    print("foodType = \(foodType), foodPrice = \(foodPrice)")}eatFood(foodType: "大盘鸡吧", foodPrice: 110)/**************************函数高级***********************///函数是引用类型, 而之前的是基础类型和值类型//两数和函数func twoNumberSum(num1:Int, num2:Int)->Int {    return num1 + num2}//两数积函数func twoNumberProduct(num1:Int, num2:Int)->Int {    return num1 * num2}//函数做函数参数<多个参数>//funcName:形参名//(Int, Int)->Int:形参funcName的类型(函数)//number1:参数2//number2:参数3func selectFunc (funcName:(Int, Int)->Int, number1:Int, number2:Int)->Int {    return funcName(number1, number2)}var cc = 90var ff = 10var seletFuncResult = selectFunc(twoNumberProduct, number1: cc, number2: ff)var seletFuncResult1 = selectFunc(twoNumberSum, number1: cc, number2: ff)print(seletFuncResult)print(seletFuncResult1)//函数作为函数的返回值func returnFunc(H:Bool)->(Int, Int)->Int {    return H ? twoNumberSum : twoNumberProduct}//调用函数returnFunc, 返回值为一个函数var returnFuncResult = returnFunc(false)//通过上步得到的函数名,在调用对应的函数var resultA = returnFuncResult(10, 10)print(resultA)//函数的嵌套//嵌套在函数内的函数, 只有它外层的函数内才可以调用,其他没有权限, 类似于OC中的私有方法print("*******************函数的嵌套***************************")func embedFunc(judge:Bool, number:Int) {    func addNumber(var num:Int) {//自增函数        print("num = \(++num)")    }    func jianNumber(var num:Int) {//自减函数        print("jianNum = \(--num)")    }    //根据条件选定不同的函数    let funcName = judge ? addNumber : jianNumber    funcName(number)}embedFunc(true, number: 20)//闭包(匿名函数), 类似于OC中的blockvar block = {(str:String)->Void in    print("str = \(str)")}block("dfdfdfd")//无参数无返回的闭包var block2 = { () in    print("oooooooo")}block2()var block3 = {(str1:String)->Void in    print("str1 = \(str1)")}block3("朝天日")/****************枚举*****************///1.定义swift中,定义枚举,枚举名首字母大写, 枚举的值的首字母也要大写(命名规范)//2.枚举值以 case 关键字开头enum Color {    case RedColor    case OrangeColor    case YellowColor    case GreenColor    case BlueColor}print(Color.RedColor.hashValue)print(Color.OrangeColor.hashValue)print(Color.BlueColor.hashValue)print(Color.GreenColor.hashValue)enum Fruit:Int {    case Apple = 6    case Banana}var fruit = Fruit.Apple.rawValueprint(fruit)//枚举的相关值//定义枚举相关值的格式实列如下enum Girl {    case Id(Int)//Id的相关值是Int型    case Info(Double, String, Int)//元组}var girl = Girl.Info(175, "jingjing", 18)//利用枚举的相关值,结合switch- case 进行值绑定switch girl {case Girl.Info(var height, var name, var age):    print("name  = \(name)")case Girl.Id(var id):    print("id = \(id)")}/************类 和 结构体****************/class Student {    //再类中,定义类的属性,由于构造方法安全原则(必须保证使用构建方法创建出来的对象的属性默认值),我们必须给属性值设置默认值    //在swift中调用属性可以使用 self. 也可以直接使用属性的名字    var name:String!    var age:Int!    //构建方法:此方法必须使用 self.    init (name:String, age:Int) {        self.name = name        self.age = age    }    init(name:String) {        self.name = name;    }    //定义类的方法    func sayHi(){        print("fuck you! my name is \(name), age is \(age)")    }}//生成一个Student类的实列let stu1 = Student(name: "shadiao", age: 12)let stu = Student(name: "xiaopanzi")//给实列的属性进行赋值stu.name = "honghong"stu.age = 19//实列方法调用stu.sayHi()stu1.sayHi()//结构体:定义以  struct 关键字打头//因为结构中有一个成员属性逐一赋值的构造方法,该方法由系统生成不需要人为创建struct StudentSTR {    //属性    var name:String    var age:Int    var hobby:String    var BWH:(Double, Double, Double)    //方法    func sayHello() {        print("hi, name is \(name), you BWH is \(BWH)")    }}//生成结构体变量var stuSTR = StudentSTR(name: "白雪", age: 18, hobby: "string Man", BWH: (30, 25, 40))stuSTR.sayHello()//给结构体赋值stuSTR.BWH = (100, 85, 65)//调用方法stuSTR.sayHello()//类和结构体的区别//1.类是引用类型,而结构体是值类型//2.//A.因为结构体是值类型,所以即使结构体中的属性被var修饰.但是结构体实例被let修饰,那么该属性的值也不是不能被修改的,    //B.类是引用类型,只要内部属性不是let,即使类的实列用的是let关键字,类的属性依然可以被修改//3.何时用类,何时用结构体?    //A.当需求是进行传递值时,进行拷贝时,选择用结构体    //B.当只是对属性和方法进行封装时,选择用结构体    //C.除此之外.都选类//4.//A.在swift中集合类是值类型,因为集合类的底层都是用结构体实现的,所以都是值类型, Int, Double,String, 枚举 都是值类型    //B.函数,闭包,类 都是引用类型//类对象赋值(值引用)var stu10 = stustu10.name = "123455"print("stu1Name = \(stu10.name), stuName = \(stu.name)")//结构体对象赋值(值拷贝)var stuSTR1 = stuSTRstuSTR1.name = "花火"print("stuSTR1_N = \(stuSTR1.name), stuSTR_N = \(stuSTR.name)")//属性//1.从调用对象来看: 分为类属性, 实例属性//2.从本身功能来看: 分为储存属性和计算属性class Animal {    //定义储存属性, 用来接收我们设置的属性值(实列属性)    var name:String = "小红红"    var isFly:Bool!    //定义懒加载属性, 只有用到的时候才会调用    lazy var isSpeak:Bool = false}//实例对象如果是可选类型的话, 调用属性会自动加问号(Xcode 6.4)//let animal:Animal? = Animal()//println(animal?.name)let animal2 = Animal()print(animal2.name)//存储属性就是为了接收保存所赋给的值animal2.name = "waGa"animal2.isFly = trueanimal2.isSpeak = falseprint("name = \(animal2.name)")class CoolPerson {    //存储属性:类似于OC中的实列变量    var name = "nana"    //计算属性:类似于OC中的属性, 有setter 和 gatter方法    var getString:String {        get{            return name + " is man"        }set{            name = newValue        }        //只读属性的简单写法//        return "nana"    }}let coolPerson = CoolPerson()coolPerson.name = "xiaomeimei"//下面一句代码, 执行coolPerson的计算属性gatString里的gat分支var getStr = coolPerson.getStringprint("getStr = \(getStr)")//下面一句代码, 执行coolPerson的计算属性gatString里的set分支coolPerson.getString = "妹妹"print("newGetStr = \(coolPerson.getString)")//属性观察器class BenzCar {    //储存属性    var carType = "CES300"    var carColor = "black"    //属性观察器 语法    var carPrice:Double = 1200000 {        willSet{//属性将要赋值时执行            print("newPrice = \(newValue)")        }didSet {//属性已经被赋值后执行            print("oldPrice = \(oldValue)")        }    }}let benzCar = BenzCar()benzCar.carPrice = 800000//属性//1.在结构体中,定义类属性用 static 关键字, 在类中 定义类属性用 class 关键字//2.在结构体中,类属性可以是计算属性和存储属性,而在类中只能是计算属性//储存属性:用于存储所付给的值//计算属性:提供一个 getter 来获取值  和 一个可选的 setter 来间接设置其他属性或变量的值class DasAuto {    //类属性用class,只能用计算属性    class var carName:String {    return "朗逸"    }}//类名直接调用print(DasAuto.carName)struct BYDCar {    //结构属性用static, 存储属性,计算属性均可    static var carName = "F4"    static var carPrice:Int {        return 12000    }}print("carName = \(BYDCar.carName), carPrice = \(BYDCar.carPrice)")/*************方法(类方法 / 实列方法)**********************/class FordCar {    var carName = "福克斯"    //实例方法    func printCarName() {        print(carName)    }    //类方法    class func printName(carName carName:String){        print(carName)    }}let fordCar = FordCar()//调用实例方法fordCar.printCarName()//调用类方法FordCar.printName(carName: "dear")/*************继承******************///1.结构体不能被继承,只有类可以被继承//2.在swift中,没有显示的声明继承于某个类的类都是基类//3.如果一个类不想被其他类继承,在类定义的class前面final, 如果一个类的计算属性, 方法不希望被子类重写  就在属性或方法的前面加 final, 如果一个子类想要重写父类的计算属性,或是方法,就必须在重写前加override .前提是父类的方法或属性可以被重写class Car {    var carName:String = "00"//存储属性    //如果一个计算属性不希望被子类重写,就在属性前加 final     final var carDiscroption:String {        return "这是一辆很牛逼的车"    }    var carSpeed:Double{//计算属性        return 350    }    //类中定义的方法,可以被子类重写 如果不想被重写就在方法前加 final 关键字//    final func sayHello {//    }    //这个实例方法,没有加约束,可以被子类重写    func sayHi(){        print("这是个父类方法")    }    //构造方法//    init(carName:String, carSpeed:Double, carDiscroption:String) {//        self.carName = carName//        self.carSpeed = carSpeed//        self.carDiscroption = carDiscroption//    }}let car = Car()car.sayHi()class QQCar:Car {    var qqCarPrice:Double!    //重写父类的计算属性,需要在属性前添加override    override var carSpeed:Double {        return 450    }    override func sayHi() {        print("这是一个重写后的方法")    }    //子类自己的方法    func run(){        print("i will run")    }}let qqCar = QQCar()qqCar.sayHi()qqCar.carName = "奇瑞QQ"qqCar.qqCarPrice = 1qqCar.run()print("carName = \(qqCar.carName), carPrice = \(qqCar.qqCarPrice)")qqCar.sayHi()class UglyPerson {    //对于那些初始化时也不一定有值可以定为可选类型    var name:String    var age:Int    var sonCount:Int?    //定制构造方法(类似于OC中的init方法)    init(name:String, age:Int) {        self.name = name        self.age = age    }    //析构方法(类似于OC中的dealloc方法)    deinit {        print("ugly persin is die")    }}var uglyPer1:UglyPerson? = UglyPerson(name: "cpp", age: 20)weak var uglyPer2:UglyPerson? = uglyPer1uglyPer1 = nil//uglyPer2 = nil//swift 的内存管理//1.使用ARC机制,当对象不在使用的时候(生命周期结束时),就会触发deinit方法销毁相应的内存空间//2.swift中的引用计数概念和OC中的略有不同,当有一个指针指向该空间的时候,为了避免内存崩溃,该内存空间不会被释放,当没有指针指向时,才会释放//3.解决swift中的循环引用,可以用weak修饰可选类型的属性 或 用 unowned 修饰非可选类型的属性,把其中一个变为若引用,打破引用循环class CreditCard {    var number:Int//卡号    var holder:Holder//持有人    //定制构造方法    init(number:Int, holder:Holder) {        self.number = number        self.holder = holder    }    //析构方法    deinit {        print("card is zhuxiao")    }}class Holder {    var name:String//姓名  weak var card:CreditCard?//不是每个人都有信用卡,定义可选类型    init(name:String) {        self.name = name    }    deinit {        print("card's holder is die")    }}var holder:Holder? = Holder(name: "feng")//给一张信用卡绑定了用户var card:CreditCard? = CreditCard(number: 12345, holder: holder!)//把一张信用卡绑定人的名下holder?.card = cardprint(holder?.card)holder = nilcard = nil
0 0