Swift中的协议
发布日期:2022-03-18 08:27:40 浏览次数:39 分类:技术文章

本文共 3651 字,大约阅读时间需要 12 分钟。

Swift中的协议

Swift中的常用协议

Equatable

Equatable 协议用于相等的比较,遵守这个协议后必须对==运算符进行重载。

struct Record: Equatable {    var wins: Int    var losses: Int}func ==(left: Record, right: Record) -> Bool {    return left.wins == right.wins && left.losses == right.losses}let recordA = Record(wins: 10, losses: 5)let recordB = Record(wins: 10, losses: 5)recordA == recordB//truerecordA != recordB//false

重载==之后,!=也可以正常使用

Comparable

Comparable协议用于比较,只需要重载<就可以了

struct Record: Equatable, Comparable {    var wins: Int    var losses: Int}func ==(left: Record, right: Record) -> Bool {    return left.wins == right.wins && left.losses == right.losses}func <(left: Record, right: Record) -> Bool {    if left.wins != right.wins {        return left.wins < right.wins    }    return left.losses > right.losses}

Record遵守Comparable协议,表示其是一个可比较的对象。

var team1Record = Record(wins: 10, losses: 3)var team2Record = Record(wins: 8, losses: 5)var team3Record = Record(wins: 8, losses: 8)var records = [team1Record, team2Record, team3Record]records.sort()

CustomStringConvertible

遵循CustomStringConvertible协议,只需要实现一个计算型的属性description

struct Record: Equatable, Comparable, CustomStringConvertible {    var wins: Int    var losses: Int    var description: String {        return "WINS: " + String(wins) + " , LOSSES: " + String(losses)    }}

这时print(team1Record) 输出的结果就为:WINS: 10 , LOSSES: 3

BooleanType

BooleanType可以让一个类型被视为一个布尔值,需要覆盖一个boolValue属性。

var boolValue: Bool {    return wins > losses}

就可以这样使用if语句:

if recordA {}

同样可以让基本类型实现BooleanType协议,这样就可以直接来进行布尔判断,如下:

extension Int: BooleanType {    public var boolValue: Bool {        return self != 0    }}var wins = 0if !wins {    print("You never win!")}

面向协议编程

运算符重载

内容来自

例如,重载+运算符,使两个Int型数组相加:

func +(left: [Int], right: [Int]) -> [Int] { // 1    var sum = [Int]() // 2    assert(left.count == right.count, "vector of same length only")  // 3    for (key, v) in enumerate(left) {      sum.append(left[key] + right[key]) // 4    }    return sum}

自定义运算符

定义一个自定义运算符有三步:

  • Name your operator命名运算符
    自定义的运算符可以是ASCII字符,如/, =, -, +, !, *, %, <, >, &, |, ^,也可以是Unicode字符。
  • Choose a type选择一个类型
    在Swift中,可以定义binary, unaryternary运算符,即一元、二元、三目运算符。
  • Assign precedence and associativity指定优先级和结合型

关键字:

  • operator
  • prefix 前缀运算符,比如 (取正+、取负- 、自增++、自减–)
  • postfix 后缀运算符,比如(自增++、自减–),这两可以前缀也可以后缀
  • infix 中缀,最常见二元运算
  • precedence 优先级的意思,取值 0~255 ,纯数字,不可以带符号,下划线,指数e/p 表示
  • associativity 结合性,可以是 left, right, 或者 none

如下,自定义运算符,使两个Int类型数组相加:

infix operator ⊕ { associativity left precedence 140 } // 1func ⊕(left: [Int], right: [Int]) -> [Int] { // 2    var sum = [Int](count: left.count, repeatedValue: 0)    assert(left.count == right.count, "vector of same length only")    for (key, v) in enumerate(left) {        sum[key] = left[key] + right[key]    }    return sum}

泛型运算符

如下,指定类型:

infix operator ⊕ { associativity left precedence 140 }func ⊕
(left: [T], right: [T]) -> [T] { // 1 var minus = [T]() assert(left.count == right.count, "vector of same length only") for (key, v) in enumerate(left) { minus.append(left[key] + right[key]) // 2 } return minus}

但是,会报错Could not find an overload for '+' that accepts the supplied arguments.。由于不知道类型,Swift不知道怎样相加。

所以,一般的做法是,先定义一个协议,再扩展原有类型:

protocol Number {  // 1    func +(l: Self, r: Self) -> Self // 2}extension Double : Number {} // 3extension Float  : Number {}extension Int    : Number {}infix operator ⊕ { associativity left precedence 140 }func ⊕
(left: [T], right: [T]) -> [T] { // 4 var minus = [T]() assert(left.count == right.count, "vector of same length only") for (key, v) in enumerate(left) { minus.append(left[key] + right[key]) } return minus}

参考

转载地址:https://windzen.blog.csdn.net/article/details/52798415 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:iOS Concurrency-队列、DispatchGroup
下一篇:Swift-泛型

发表评论

最新留言

能坚持,总会有不一样的收获!
[***.219.124.196]2024年04月22日 22时59分33秒