Merge pull request #301 from oldcodeoberyn/gh-pages

更新协议一章,添加新的两个小节
This commit is contained in:
梁杰
2014-09-04 21:59:22 +08:00
4 changed files with 131 additions and 17 deletions

View File

@ -657,7 +657,7 @@ if let definiteString = assumedString {
<a name="assertions"></a>
## 断言
可选类型可以让你判断值是否存在,你可以在代码中优雅地处理值缺失的情况。然而,在某些情况下,如果值缺失或者值并不满足特定的条件,你的代码可能并不需要继续执行。这时你可以在你的代码中触发一个_断言assertion_来结束代码运行并通过调试来找到值缺失的原因。
可选类型可以让你判断值是否存在,你可以在代码中优雅地处理值缺失的情况。然而,在某些情况下,如果值缺失或者值并不满足特定的条件,你的代码可能没办法继续执行。这时你可以在你的代码中触发一个_断言assertion_来结束代码运行并通过调试来找到值缺失的原因。
### 使用断言进行调试
@ -673,9 +673,9 @@ assert(age >= 0, "A person's age cannot be less than zero")
// 因为 age < 0所以断言会触发
```
在这个例子中,只有`age >= 0`为`true`的时候代码运行才会继续,也就是说,当`age`的值非负的时候。如果`age`的值是负数,就像代码中那样,`age >= 0`为`false`,断言被触发,结束应用。
在这个例子中,只有`age >= 0`为`true`的时候,即`age`的值非负的时候,代码运行才会继续。如果`age`的值是负数,就像代码中那样,`age >= 0`为`false`,断言被触发,结束应用。
断言信息不能使用字符串插值。断言信息可以省略,就像这样:
断言信息如果不需要,可以省略,就像这样:
```swift
assert(age >= 0)

View File

@ -167,30 +167,29 @@ println("unusualMenagerie has \(countElements(unusualMenagerie)) characters")
<a name="concatenating_strings_and_characters"></a>
## 连接字符串和字符 (Concatenating Strings and Characters)
字符串和字符的值可以通过加法运算符(`+`)相加在一起并创建一个新的字符串
字符串可以通过加法运算符(`+`)相加在一起(或称“串联”)并创建一个新的字符串:
```swift
let string1 = "hello"
let string2 = " there"
let character1: Character = "!"
let character2: Character = "?"
let stringPlusCharacter = string1 + character1 // 等于 "hello!"
let stringPlusString = string1 + string2 // 等于 "hello there"
let characterPlusString = character1 + string1 // 等于 "!hello"
let characterPlusCharacter = character1 + character2 // 等于 "!?"
var welcome = string1 + string
// welcome 现在等于 "hello there"
```
您也可以通过加法赋值运算符 (`+=`) 将一个字符串或者字符添加到一个已经存在字符串变量上:
您也可以通过加法赋值运算符 (`+=`) 将一个字符串添加到一个已经存在字符串变量上:
```swift
var instruction = "look over"
instruction += string2
// instruction 现在等于 "look over there"
// instruction 现在等于 "look over there"
var welcome = "good morning"
welcome += character1
// welcome 现在等于 "good morning!"
```
你可以用将`append`方法将一个字符附加到一个字符串变量的尾部:
```swift
let exclamationMark: Character = "!"
welcome.append(exclamationMark)
// welcome 现在等于 "hello there!"
```
> 注意:

View File

@ -9,13 +9,15 @@
- [协议的语法Protocol Syntax](#protocol_syntax)
- [对属性的规定Property Requirements](#property_requirements)
- [对方法的规定Method Requirements](#method_requirements)
- [对突变方法的规定Mutating Method Requirements](#mutating_method_requirements)
- [对突变方法的规定Mutating Method Requirements](#mutating_method_requirements)
- [对构造器的规定Initializer Requirements](#initializer_requirements)
- [协议类型Protocols as Types](#protocols_as_types)
- [委托(代理)模式Delegation](#delegation)
- [在扩展中添加协议成员Adding Protocol Conformance with an Extension](#adding_protocol_conformance_with_an_extension)
- [通过扩展补充协议声明Declaring Protocol Adoption with an Extension](#declaring_protocol_adoption_with_an_extension)
- [集合中的协议类型Collections of Protocol Types](#collections_of_protocol_types)
- [协议的继承Protocol Inheritance](#protocol_inheritance)
- [类专属协议Class-Only Protocol](#class_only_protocol)
- [协议合成Protocol Composition](#protocol_composition)
- [检验协议的一致性Checking for Protocol Conformance](#checking_for_protocol_conformance)
- [对可选协议的规定Optional Protocol Requirements](#optional_protocol_requirements)
@ -208,6 +210,60 @@ lightSwitch.toggle()
//lightSwitch 现在的值为 .On
```
<a name="initializer_requirements"></a>
## 对构造器的规定
协议可以要求它的遵循类型实现特定的构造器。你可以像书写普通的构造器那样,在协议的定义里写下构造器的需求,但不需要写花括号和构造器的实体:
```swift
protocol SomeProtocol {
init(someParameter: Int)
}
```
**协议构造器规定在类中的实现**
你可以在遵循该协议的类中实现构造器,并指定其为类的特定构造器或者便捷构造器。在这两种情况下,你都必须给构造器实现标上"required"修饰符:
```swift
class SomeClass: SomeProtocol {
required init(someParameter: Int) {
//构造器实现
}
}
```
使用`required`修饰符可以保证:所有的遵循该协议的子类,同样能为构造器规定提供一个显式的实现或继承实现。
关于`required`构造器的更多内容,请参考<a href="https://developer.apple.com/library/prerelease/ios/documentation/Swift/Conceptual/Swift_Programming_Language/TheBasics.html#//apple_ref/doc/uid/TP40014097-CH5-XID_454">`required`构造器 </a>
>注意
>
>如果类已经被“final”修饰符所标示你就不需要在协议构造器规定的实现中使用"required"修饰符。因为final类不能有子类。关于`final`修饰符的更多内容,请参见<a href="https://developer.apple.com/library/prerelease/ios/documentation/Swift/Conceptual/Swift_Programming_Language/Initialization.html#//apple_ref/doc/uid/TP40014097-CH18-XID_339">防止重写</a>
如果一个子类重写了父类的指定构造器,并且该构造器遵循了某个协议的规定,那么该构造器的实现需要被同时标示`required``override`修饰符
```swift
protocol SomeProtocol {
init()
}
class SomeSuperClass {
init() {
//协议定义
}
}
class SomeSubClass: SomeSuperClass, SomeProtocol {
// "required" from SomeProtocol conformance; "override" from SomeSuperClass
required override init() {
// 构造器实现
}
}
```
<a name="protocols_as_types"></a>
## 协议类型
@ -524,6 +580,23 @@ println(game.asPrettyText())
// ○ ○ ▲ ○ ○ ▲ ○ ○ ▲ ▲ ○ ○ ○ ▼ ○ ○ ○ ○ ▼ ○ ○ ▼ ○ ▼ ○
```
<a name="class_only_protocol"></a>
## 类专属协议
你可以在协议的继承列表中,通过添加“class”关键字,限制协议只能适配到类class类型。结构体或枚举不能遵循该协议。该“class”关键字必须是第一个出现在协议的继承列表中其后才是其他继承协议。
```swift
protocol SomeClassOnlyProtocol: class, SomeInheritedProtocol {
// class-only protocol definition goes here
}
```
在以上例子中协议SomeClassOnlyProtocol只能被类class类型适配。如果尝试让结构体或枚举类型适配该协议则会出现编译错误。
>注意
>
>当协议需求定义的行为,要求(或假设)它的遵循类型必须是引用语义而非值语义时,应该采用类专属协议。关于引用语义,值语义的更多内容,请查看<a href="https://developer.apple.com/library/prerelease/ios/documentation/Swift/Conceptual/Swift_Programming_Language/ClassesAndStructures.html#//apple_ref/doc/uid/TP40014097-CH13-XID_145">结构体和枚举是值类型</a>和<a href="https://developer.apple.com/library/prerelease/ios/documentation/Swift/Conceptual/Swift_Programming_Language/ClassesAndStructures.html#//apple_ref/doc/uid/TP40014097-CH13-XID_146">类是引用类型</a>
<a name="protocol_composition"></a>
## 协议合成

View File

@ -23,6 +23,48 @@
声明特性只能应用于声明。然而,你也可以将`noreturn`特性应用于函数或方法类型。
`availability`
`availability`特性用于声明时,将表示该声明的生命周期会依赖于特定的平台和操作系统版本。
`availability`特性总会与参数列表一同出现该参数列表至少有两个参数参数之间由逗号分隔。第一个参数由以下这些平台名字中的一个起头iOS, iOSApplicationExtension, OSX, or OSXApplicationExtension。当然你也可以用一个星号(*)来表示,该声明在上面提到的所有平台上都是有效的。剩下的参数,可以以任何顺序出现,并且可以附加关于声明生命周期的附加信息,包括重要的里程碑。
- `unavailable`参数表示该声明在特定的平台上是无效的
- `introduced`参数表示:特定的平台上,该声明被使用的第一个版本。格式如下:<p>`introduced=version number`<p>这个version number由一个正的十进制整数或浮点数构成。
- `deprecated`参数表示:特定的平台上,该声明被建议弃用的第一个版本。格式如下:
<p>`deprecated=version number`<p>这个version number由一个正的十进制整数或浮点数构成。
- `obsoleted`参数表示:特定的平台上,该声明被弃用的第一个版本。格式如下:
<p>`deprecated=version number`<p>这个version number由一个正的十进制整数或浮点数构成。
The message argument is used to provide a textual message thats displayed by the compiler when emitting a warning or error about the use of a deprecated or obsoleted declaration. It has the following form:
message=message
The message consists of a string literal.
The renamed argument is used to provide a textual message that indicates the new name for a declaration thats been renamed. The new name is displayed by the compiler when emitting an error about the use of a renamed declaration. It has the following form:
renamed=new name
The new name consists of a string literal.
You can use the renamed argument in conjunction with the unavailable argument and a type alias declaration to indicate to clients of your code that a declaration has been renamed. For example, this is useful when the name of a declaration is changed between releases of a framework or library.
// First release
protocol MyProtocol {
// protocol definition
}
// Subsequent release renames MyProtocol
protocol MyRenamedProtocol {
// protocol definition
}
@availability(*, unavailable, renamed="MyRenamedProtocol")
typealias MyProtocol = MyRenamedProtocol
You can apply multiple availability attributes on a single declaration to specify the declarations availability on different platforms. The compiler uses an availability attribute only when the attribute specifies a platform that matches the current target platform.
`assignment`
该特性用于修饰重载了复合赋值运算符的函数。重载了复合赋值运算符的函数必需将它们的初始输入参数标记为`inout`。如何使用`assignment`特性的一个例子,请见:[复合赋值运算符]()。