Swift学习之分支语句之guard

本文深入解析Swift中的Guard语句,展示其如何简化复杂的条件检查,提高代码的可读性和维护性。通过示例对比if-else与Guard的不同应用,以及如何使用Guard进行错误处理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  • guard(守护警卫)语句是Swift2之后新添加的关键字,与if语句非常类似,可以在判断一个条件为true的情况下执行某语句,否则终止或跳过执行某语句。它的设计目的是替换复杂的if-else语句嵌套,提高程序的可读性。
  • guard语句语法:
guard 条件表达式 else {
跳转语句
}
语句组

Swift中跳转语句跳转语句一般是returnbreakcontinuethrow,其中returnthrow可以用于guard。return是返回,即不在执行后面的语句组;throw是抛出异常,抛出异常后执行throw语句,也不再执行后面的语句组。

  • 示例1:用if-else嵌套的复杂语句
func if_elseStyleBlog(blog: Blog){
    if let blogName = blog.Name{
          print("这篇博客名字为:\(blogName)")
        if let blogURL = blog.URL{
            print("这篇博地址为:\(blogURL)")
            if let blogAuthor = blog.Author{
               print("这篇博客作者为:\(blogAuthor)")
            }else{
               print("这篇博客没有作者!")
            }
        }else{
            print("这篇博客没有网址!")
        }
    }else{
       print("这篇博客没有名字!")
    }
}

如果使用guard实现同样的功能:

func guardLogStyleBlog(blog:Blog){
    guard let blogName = blog.Name else {
        print("这篇博客没有名字!")
        return
    }
    print("这篇博客名字为:\(blogName)")
    
    guard let blogURL = blog.URL else {
        print("这篇博客没有网址!")
        return
    }
    print("这篇博地址为:\(blogURL)")
    
    guard let blogAuthor = blog.Author else {
        print("这篇博客没有作者!")
        return
    }
    print("这篇博客作者为:\(blogAuthor)")
}

由上面可以看出guard可以使一些比较复杂循环判断更简洁,同时guard可以实现可选值绑定。

  • 示例2:guard跳转语句使用throw来模拟一下数组和角标的关系
//定义一个数组报错的枚举
enum arrayError: Error {
    case indexCrossBoard, indexLessZero, arrayIsEmpty
}
//获取数据元素的方法,在参数后面中加入throws关键字标记该方法,在方法体内部使用throw抛出具体的错误类型。
func getObjByIndex(index:Int) throws -> Int {
    let array = [1,2,3,4,5]
    //index必须小于array的cont
    guard index < array.count else { throw arrayError.indexCrossBoard }
    //index必须大于等于0
    guard index >= 0 else { throw arrayError.indexLessZero }
    //数组不能为空
    guard array.count > 0 else { throw arrayError.arrayIsEmpty }
    print(array[index])
    return array[index]
}
//调用方法,有抛出就一定有接收,所以方法在被调用时会被强制加上`do catch try`关键字,不然编译器会报错。
do {
    let _:Int = try getObjByIndex(index: 5)
} catch arrayError.indexCrossBoard {
    print("数组脚标越界")
} catch arrayError.indexLessZero {
    print("数组角标不能为负数")
} catch arrayError.arrayIsEmpty {
    print("/数组不能为空")
} catch {
    
}

结果为数组脚标越界,当一个方法体被throws关键字标记后的方法代表它可能会向外抛出错误,这个错误可以是自定义的,可以取自上面自定义的枚举。

上面抛出异常的写法虽然看着比较简单明了,但是不叫臃肿,每次调用都要写do catch try,我们可以封装成一个回调的闭包。

//定义一个闭包
typealias ArrayErrorCallback = () throws -> Bool
//定义方法
func checkObjectById(index:Int, errorBlock:@escaping (_ inner:ArrayErrorCallback) -> Void) {
    let array = [1,2,3,4,5]
    if index < array.count && index >= 0 {
        // throw error
        errorBlock({ throw arrayError.indexCrossBoard })
    }
    if index < 0 {
       errorBlock({ throw arrayError.indexLessZero })
    }
    if  array.count == 0 {
        errorBlock({ throw arrayError.arrayIsEmpty })
    }
    // return value
    errorBlock({return true})
}
//调用方法
checkObjectById(index:-5) { (inner: ArrayErrorCallback) -> Void in
    do {
        let success = try inner()
        print(success)
    } catch {
        print(error)
}
}

用法差不多,只是把throws标记在闭包上。更适合异步操作的场景。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值