协议和扩展

在Objective-C中,协议是很常见也非常重要的一个特性,Swift中也保留了协议,语法略有变化。

用protocol关键字声明一个协议:

  1. protocol ExampleProtocol {
  2. var simpleDescription: String { get }
  3. mutating func adjust()
  4. }

类、结构、枚举型都可以遵守协议:

  1. class SimpleClass: ExampleProtocol {
  2. var simpleDescription: String = "A very simple class."
  3. var anotherProperty: Int =
  4. func adjust() {
  5. simpleDescription += " Now 100% adjusted."
  6. }
  7. }
  8. var a = SimpleClass()
  9. a.adjust()
  10. let aDescription = a.simpleDescription
  11.  
  12. struct SimpleStructure: ExampleProtocol {
  13. var simpleDescription: String = "A simple structure"
  14. mutating func adjust() {
  15. simpleDescription += " (adjusted)"
  16. }
  17. }
  18. var b = SimpleStructure()
  19. b.adjust()
  20. let bDescription = b.simpleDescription

注意在结构体的方法先用mutating关键字来标识该方法会改变结构体,而类声明中不需要给任何方法加此关键字,因为类的任何方法都可以改变类。

用extension给现有的类型增加功能,比如新的方法或者计算过的属性等。

也可以通过extension来给一个类型添加对某个协议的遵守,这个类型可以是在别的地方声明的,甚至是从第三方库或框架导入的。

  1. extension Int: ExampleProtocol {
  2. var simpleDescription: String {
  3. return "The number \(self)"
  4. }
  5. mutating func adjust() {
  6. self +=
  7. }
  8. }
  9. println(.simpleDescription) //The number 7

协议的名字可以像其他具名的类型名字一样被使用,比如创建一个包含很多对象的集合,这些对象都是不同的类型,但是它们都遵守同一个协议。当处理那些类型为某个协议的变量时,协议之外声明和定义的方法将无法调用。

  1. let protocolValue: ExampleProtocol = a
  2. println(protocolValue.simpleDescription)
  3. println(protocolValue.anotherProperty) // Uncomment to see the error

尽管protocolValue变量的运行时类型是SimpleClass,编译器仍然会将它看做显示指定的ExampleProtocol类型,这意味着你不能调用那些在SimpleClass中除了遵守ExampleProtocol协议之外定义的其他方法。

泛型(Generics)

用尖括号包含一个名字来创建一个泛型函数或者类型

  1. func repeat<Item>(item: Item, times: Int) -> [Item] {
  2. var result = [Item]()
  3. for i in ..<times {
  4. result.append(item)
  5. }
  6. return result
  7. }
  8. repeat("knock", )

可以创建泛型格式的函数、方法、类、枚举类型、结构体。

  1. enum OptionalValue<T> {
  2. case None
  3. case Some(T)
  4. }
  5. var possibleInteger: OptionalValue<Int> = .None
  6. possibleInteger = .Some()

在类型名之后用where来指明一系列要求,比如要求某个数据类型来实现某个协议,要求两个类型必须相同,或者要求某个类必须拥有指定的基类

  1. func anyCommonElements <T, U where T: SequenceType, U: SequenceType, T.Generator.Element: Equatable, T.Generator.Element == U.Generator.Element> (lhs: T, rhs: U) -> Bool {
  2. for lhsItem in lhs {
  3. for rhsItem in rhs {
  4. if lhsItem == rhsItem {
  5. return true
  6. }
  7. }
  8. }
  9. return false
  10. }
  11. anyCommonElements([, , ], []) //true

简单的情况下,可以省略where而直接在冒号后面写协议或者类名,<T:Equatable>和<T where T:Equtable>是等价的。

Swift学习笔记三的更多相关文章

  1. Swift 学习笔记 (三) 之循环引用浅析

    原创:转载请注明出处 110.自动引用计数实践 下面的例子展示了自动引用计数的工作机制.例子以一个简单的Person类开始,并定义了一个叫name的常量属性: class Person {     l ...

  2. Swift学习笔记(一)搭配环境以及代码运行成功

    原文:Swift学习笔记(一)搭配环境以及代码运行成功 1.Swift是啥? 百度去!度娘告诉你它是苹果最新推出的编程语言,比c,c++,objc要高效简单.能够开发ios,mac相关的app哦!是苹 ...

  3. Oracle学习笔记三 SQL命令

    SQL简介 SQL 支持下列类别的命令: 1.数据定义语言(DDL) 2.数据操纵语言(DML) 3.事务控制语言(TCL) 4.数据控制语言(DCL)  

  4. 【swift学习笔记】二.页面转跳数据回传

    上一篇我们介绍了页面转跳:[swift学习笔记]一.页面转跳的条件判断和传值 这一篇说一下如何把数据回传回父页面,如下图所示,这个例子很简单,只是把传过去的数据加上了"回传"两个字 ...

  5. [Firefly引擎][学习笔记三][已完结]所需模块封装

    原地址:http://www.9miao.com/question-15-54671.html 学习笔记一传送门学习笔记二传送门 学习笔记三导读:        笔记三主要就是各个模块的封装了,这里贴 ...

  6. JSP学习笔记(三):简单的Tomcat Web服务器

    注意:每次对Tomcat配置文件进行修改后,必须重启Tomcat 在E盘的DATA文件夹中创建TomcatDemo文件夹,并将Tomcat安装路径下的webapps/ROOT中的WEB-INF文件夹复 ...

  7. java之jvm学习笔记三(Class文件检验器)

    java之jvm学习笔记三(Class文件检验器) 前面的学习我们知道了class文件被类装载器所装载,但是在装载class文件之前或之后,class文件实际上还需要被校验,这就是今天的学习主题,cl ...

  8. VSTO学习笔记(三) 开发Office 2010 64位COM加载项

    原文:VSTO学习笔记(三) 开发Office 2010 64位COM加载项 一.加载项简介 Office提供了多种用于扩展Office应用程序功能的模式,常见的有: 1.Office 自动化程序(A ...

  9. Java IO学习笔记三

    Java IO学习笔记三 在整个IO包中,实际上就是分为字节流和字符流,但是除了这两个流之外,还存在了一组字节流-字符流的转换类. OutputStreamWriter:是Writer的子类,将输出的 ...

随机推荐

  1. solr4.2 solrconfig.xml配置文件简单介绍

    对于solr4.x的每个core有两个很重要的配置文件:solrconfig.xml和schema.xml,下面我们来了解solrconfig.xml配置文件. 具体很详细的内容请细读solrcofi ...

  2. link 参数

    -all-static do not do any dynamic linking at all -avoid-version do not add a version suffix if possi ...

  3. Oracle 存储过程动态建表

    动态sql,顾名思义就是动态执行的sql,也就是说在没执行之前是动态的拼接的. 任务 传入参数:新建的表名hd+当前的年和月,例如hd_201105表结构是:字段1:id ,类型是number,可以自 ...

  4. strcpy函数和strncpy函数的区别

    strcpy函数和strncpy函数的原型介绍在我的另一篇文章中介绍了,见strcpy,strncpy,strlen等函数原型 strcpy:字串复制 原型:char *strcpy(char *de ...

  5. android 官网处理图片 代码

    /** * 获取压缩后的图片 (官网大图片加载对应代码) * * @param res * @param resId * @param reqWidth * 所需图片压缩尺寸最小宽度 * @param ...

  6. iOS学习网站及大牛网址(实时更新)

    iOS学习网站及大牛网址(实时更新) 学习网站 https://github.com/Tim9Liu9/TimLiu-iOS  自己总结的iOS.mac开源项目及库 https://github.co ...

  7. C#快速排序详解

    使用快速排序法对一列数字进行排序的过程 快速排序使用分治法(Divide and conquer)策略来把一个序列(list)分为两个子序列(sub-lists). 步骤为: 从数列中挑出一个元素,称 ...

  8. C语言相关图书推荐

    C Primer Plus(第5版 中文版) 作      者 [美] 普拉塔(Prata S.) 著:云巅工作室 编 出 版 社 人民邮电出版社 出版时间 2005-02-01 版      次 1 ...

  9. HDU5727 Necklace

    http://acm.hdu.edu.cn/showproblem.php?pid=5727 题意:n个珠子,每个珠子有阴阳两种属性,且阴的一定和阳的紧邻,排成一个环:m行,每行两个数,表示阳性x珠子 ...

  10. 解决PHP5.3.x下ffmpeg安装配置问题

    本人的环境: OS : windows 7 64位 WAMP:2.1a PHP:5.3.3(之前是5.3.13) 项目需要用ffmpeg-php实现上传视频转码截图等功能,但是找了很多资料都没有把ff ...