编辑代码

import Foundation

/*:
## 1. 请问下面哪种写法更符合Swift规范,为什么?
 ```
 1.
 func compare(_ result: ComparisonResult) {
     switch result {
     case .orderedAscending:
         print("orderedAscending")
     case .orderedDescending:
         print("orderedDescending")
     case .orderedSame:
         print("orderorderedSameedDescending")
     default:
         break
     }
 }
 
 2.
 func compare(_ result: ComparisonResult) {
     switch result {
     case ComparisonResult.orderedAscending:
         print("orderedAscending")
     case ComparisonResult.orderedDescending:
         print("orderedDescending")
     case ComparisonResult.orderedSame:
         print("orderorderedSameedDescending")
     default:
         break
     }
 }
 ```
 */

print("第一种")
/*
 两种写法的区别就是switch-case语句中,对于枚举类型判断的写法不同
 在函数声明中,已经将result声明为ComparisonResult枚举类型
 那么后续【赋值】或者【比较判断】都应该用更简洁的形式:省略枚举类型,直接用点语法的方式
*/

/*:
## 2. 下面的代码如何使用Swift的枚举简化实现?(提示:1. 需要借助枚举的关联值;2. 可以在枚举中定义方法。)
 ```
 class Weapon {
     var length = 0.0
     var weigt = 0.0
     
     func desc() -> String {
         return "length = \(aGun.length), weigt = \(aGun.weigt)"
     }
 }

 class Gun: Weapon {

 }

 class Knife: Weapon {

 }

 let aGun = Gun()
 aGun.length = 40
 aGun.weigt = 10

 let aKnife = Knife()
 aKnife.length = 40
 aKnife.weigt = 10

 print(aGun.desc())
 print(aKnife.desc())
 ```
 */

// 题目那个Weapon类,desc函数实现不太对
// 感觉这个题目,如果Gun、Knife类添加一些自己的属性,然后重写desc,更有实例的感觉,改写的理由也更充分

enum Weapon {
    case gun(Int, Int)
    case knife(Int, Int)

    func desc() -> String {
        switch self {
            case .gun(let length, let weight):
                return "length = \(length), weight = \(weight)"
            case .knife(let length, let weight):
                return "length = \(length), weight = \(weight)"
        }
    }
}

let aGun = Weapon.gun(40, 10)
let aKnife = Weapon.knife(40, 10)

print(aGun.desc())
print(aKnife.desc())

/*:
## 3. 了解枚举递归用法即可。
 
 */

 // 定义:枚举的枚举成员有使用该枚举值作为关联值的枚举为递归枚举

 indirect enum A {
     case aa(Int)
     case bb(A)
     case cc(A, A)
 }

enum B {
     case aa
     indirect case bb(B)
     indirect case cc(B, B)
 }

 let a1 = A.aa(33)
 let a2 = A.bb(a1)
 let a3 = A.cc(a1, a1)

/*:
## 4. 选做:
 Swift中哪些类型可以直接在枚举中声明,类似Int,能写成 enum SortOrder: Int的形式,为什么?(提示,搜索swift RawRepresentable)
 */

 // 字符串、整型、浮点型

 /* enum实现了RawRepresentable协议
    该协议定义了应该rawValue,可以在构造方法中设置RawValue,然后get方法中获取RawValue
    类似一个计算属性
 */




/*:
## 5. 对于以下代码,会输出什么,为什么?如果希望对aDic改变同步到aDic1该怎么做?
 
 var aDic = ["123" : "abc"]
 var aDic1 = aDic

 aDic["123"] = "vvv"
 print("aDic is \(aDic), aDic1 is \(aDic1)")
 
 */

print("aDic is vvv, aDic1 is abc")
 // dic其实是struct,是值类型,赋值时相当于直接复制一份
 // 尝试将adic1为UnsafePointer类型,不过不会创建

/*:
## 6. 以下代码为什么有问题,用let声明值类型和引用类型需要注意什么。
 ```
 struct People {
     var name: String?
 }

 class Person {
     var name: String?
 }

 let somePeople = People()
 somePeople.name = "xiaohong"

 let somePerson = Person()
 somePerson.name = "xiaoming"
 ```
 */

/*
struct是值类型,class是引用类型
let struct相当于这个struct不可变,所以第一个赋值失败
let class相当于这个指针本身不可变,但是其所指内存对应对象是可以改的,所以第二个赋值是可以的
*/


/*:
## 7. 了解如何在在结构和类之间进行选择
 [在在结构和类之间进行选择](https://developer.apple.com/documentation/swift/choosing_between_structures_and_classes)
 */



/*:
## 8. 了解属性包装器 计算属性 属性观察器 类属性
*/

// 属性包装器
/*
使用@propertyWrapper创建一个struct作为包装器,其中包含一个wrappedValue的属性。
对struct或者class的属性之前加上@+对应属性包装器struct名即可
注:属性包装器的wrappedValue的类型和修饰属性是一样的
*/

// 计算属性 --  是不是抄现在主流node.js前端框架的
/*
计算属性不向储存属性,是没有实际存值的,每次getter/setter都是相当于调用了方法
计算属性可以有setter和getter,也可以只有getter(此时可以省略get关键字),setter方法可以有参数,无参数是默认提供一个叫newValue的参数
*/

// 属性观察器 --  是不是抄现在主流node.js前端框架的
/*
可以对属性添加willSet和didSet方法监听其变化,这里set方法可以自己设置参数名,也有默认参数名:newVaule/oldValue
*/

// 类属性
/*
实例属性属于类实例化的对象,类属性属于类本身,所有该类的实例共享一份
可以在属性前面加static关键字声明为类属性
也可以使用class关键字,此时类属性将可继承
*/