在一些语言中,有try/finally这样的控制语句,比如Java。

这种语句可以让我们在finally代码块中执行必须要执行的代码,不管之前怎样的兴风作浪。

在Swift 2.0中,Apple提供了defer关键字,让我们可以实现同样的效果。

func checkSomething() {print("CheckPoint 1")doSomething()print("CheckPoint 4")}func doSomething() {print("CheckPoint 2")defer {print("Clean up here")}print("CheckPoint 3")}checkSomething() // CheckPoint 1, CheckPoint 2, CheckPoint 3, Clean up here, CheckPoint 4

上述示例可以看到,在打印出“CheckPoint 2”之后并没有打印出“Clean up here”,而是“CheckPoint 3”,这就是defer的作用,它对进行了print("Clean up here")延迟。我们再来看一个I/O的示例:

// 伪代码
func writeSomething() {let file = OpenFile()let ioStatus = fetchIOStatus()guard ioStatus != "error" else {return}file.write()closeFile(file)}

上述示例是一个I/O操作的伪代码,如果获取到的ioStatus正常,那么该方法没有问题,

如果ioStatus取到的是error,那么会被guard语句抓到执行return操作,

这样的话closeFile(file)就永远都不会执行了,一个严重的Bug就这样产生了。下面我们看看如何用defer来解决这个问题:

// 伪代码
func writeSomething() {let file = OpenFile()defer {closeFile(file)}let ioStatus = fetchIOStatus()guard ioStatus != "error" else {return}file.write()}

我们将closeFile(file)放在defer代码块里,这样即使ioStatuserror,在执行return前会先执行defer里的代码,这样就保证了不管发生什么,最后都会将文件关闭。

需要注意的是, 虽然说defer的内容会在return之前执行, 但是如果defer定义在return之后, 那么还是不会执行defter的内容, 也就是说, defer关键字必须比return早出现。

放在return之后:

var str = "Hello, playground"func show() {print("这里是即将要推迟(但一定会)执行的代码")
}func test() {if str.characters.count >= 2 {print("跳出该方法的执行")return}defer {show()}
}test()  // 输出结果: 跳出该方法的执行

放在return之前:

var str = "Hello, playground"func show() {print("这里是即将要推迟(但一定会)执行的代码")
}func test() {defer {show()}if str.characters.count >= 2 {print("跳出该方法的执行")return}
}test()  // 输出结果: 跳出该方法的执行 这里是即将要推迟(但一定会)执行的代码

Swift - defer关键字(推迟执行)相关推荐

  1. Go语言defer关键字

    Go语言的defer关键字用于延迟调用,下面是关于Go语言defer关键字的一些基础概念: 1. defer关键字用于注册延迟调用: 2. 这些调用直到包含当前该defer关键字的函数执行完了才会被执 ...

  2. Swift之常见闭包与defer关键字的使用分析和闭包中的循环引用 | CSDN创作打卡

    一.什么是闭包? 在 Swift 中,可以通过 func 定义一个函数,也可以通过闭包表达式定义一个函数,闭包是一个捕获了上下文的常量或者是变量的函数.闭包(Closures)是自包含的功能代码块,可 ...

  3. Go 语言编程 — defer 关键字

    目录 文章目录 目录 defer 关键字 defer 的用途之一:释放资源 defer 的用途之二:执行 recover(恢复) defer 特性 多个 defer 的执行顺序 被 deferred ...

  4. mysql 关键字的优先级_mySQL之关键字的执行优先级讲解

    如下所示: from 表 where 条件 group by 字段 形成虚拟的表及字段,聚合及字段添加 having 筛选数据 distinct 去重 order by 字段 asc,desc lim ...

  5. Swift 使用WebKit动态执行javascript脚本

    Swift 使用WebKit动态执行javascript脚本 由于苹果取消UIWebView的控件使用.在IOS12 改用WebKit,需要导入头文件.swift里面需要引入相关依赖.苹果推荐我们使用 ...

  6. mysql关键字使用顺序_MySQL数据库之单表查询中关键字的执行顺序

    MySQL数据库之单表查询中关键字的执行顺序 1 语法顺序 select distinct from where group by having order by limit 2 执行顺序 from ...

  7. MySQL关键字的执行顺序分析

    文章目录 现实遇到的问题 SQL查询 常用关键字 书写顺序 执行顺序 关键字常见疑问 1. on和join执行顺序 2. cross join on执行顺序 3. on和where的区别 4. whe ...

  8. mysql数据库查询关键字级别_MySQL数据库之单表查询中关键字的执行顺序

    MySQL数据库之单表查询中关键字的执行顺序 1 语法顺序 select distinct from where group by having order by limit 2 执行顺序 from ...

  9. Go语言之全局变量定义、函数内部局部变量定义和defer关键字和值类型与引用类型

    定义全局变量函数必须使用var + 名 + type = ?进行定义 而定义局部变量(函数内部的变量)可使用 名:=?直接简短声明定义 defer 当函数的return执行完后,才执行用defer声明 ...

最新文章

  1. pynput使用简单说明
  2. pandas.DataFrame.to_dict()的使用详解
  3. 一份详细的“入坑Phd指南”---教你如何做笔记、整理参考书目、管理时间、如何写作、对自己和导师合理预期...
  4. CES2018:英特尔披露量子计算和神经拟态计算研究最新进展
  5. Ubuntu 14.04.1 安装 python mysqldb
  6. java小练习:.根据输入的月份,判断该月份有多少天
  7. Caffe 初识,揭开面纱
  8. Python virtualenv激活与退出虚拟环境
  9. python调用bat_python windows 远程执行bat
  10. ajax传递json对象 php,PHP传递通过AJAX传递JSON对象数组到前台,前台解析,遍历JSON...
  11. Lesson 73-74 The quality of our lives
  12. 从源码分析HashSet集合
  13. Django文件上传与下载
  14. 前端是什么,是干嘛的
  15. Layui同一个表单中放置两个按钮,提交问题
  16. 关于sbb eax, eax以及sbb eax, 0FFFFFFFFh指令连用
  17. SpringBoot里参数校验/参数验证
  18. python绘图报错
  19. 无法访问此网站 localhost 拒绝了我们的连接请求。
  20. 使用UltraISO软碟通离线安装Centos8.3.2011过程中遇到的问题

热门文章

  1. c语言中post协议,c/c++的http协议的get和post方法
  2. SearchParams(URL获取参数)
  3. 7-56 互评成绩 (25 分) (排序题)
  4. 7-1 一元多项式求导 (10 分)
  5. sun-java6-jdk_Ubuntu下安装sun-java6-jdk和eclipse
  6. 树莓派编译mysql卡死_关于树莓派编译工作空间卡死情况的解决办法
  7. web页面找不到资源文件,报404,但是资源文件存在且路径没错
  8. css实现两端对齐的3种方法
  9. 【转】Burp Suite详细使用教程-Intruder模块详解
  10. (5):Silverlight 2 实现简单的拖放功能