1. 程式人生 > Android開發 >Swift5.2-基本的操作(中文檔案)

Swift5.2-基本的操作(中文檔案)

引言

繼續學習Swift檔案,從上一章節:基礎,我們學習了Swift基礎,現在,我們學習Swift的基本操作。這一章節的內容比較簡單,一些運運算元操作基本上和C、OC上的一樣,不過在Swift上也有它特有的一些運運算元,可以簡化程式碼,如**??操作符、...操作符、..<**操作符和單邊值域,不熟悉的朋友可以單獨去看這部分內容(在7、8、9三個小節),其他的運運算元就可以跳過了。由於篇幅較長,這裡分篇來記錄,接下來,開始吧!

如果你已經掌握了Swift的基礎,那麼請參閱下一章節:字串和字元

基本的操作

運運算元是用於檢查、更改或組合值的特殊符號或短語。例如,加法運運算元(+)將兩個數字相加,如let i = 1 + 2;邏輯和運運算元(&&)組合兩個布林值,如if enteredDoorCode && passedRetinaScan。

Swift支援大多數標準的C操作符,並改進了一些功能,以消除常見的編碼錯誤。賦值操作符(=)不返回值,以防止在使用equal to操作符(==)時錯誤地使用它。算術運運算元(+、-、*、/、%等等)檢測並禁止值溢位,以避免在處理大於或小於儲存它們的型別允許的值範圍的數字時出現意外結果。您可以使用Swift的溢位操作符(如溢位操作符中所述)來選擇對溢位行為進行值設定。

Swift還提供了C中沒有的範圍操作符,比如a..< b和a…b作為表示值範圍的快捷方式。

本章介紹了Swift中常用的操作符。高階操作符涵蓋Swift的操作符,並描述如何定義您自己自定義操作符和實現標準操作符為您自己自定義型別。

1 術語

運運算元有一元、二元或三元:

  • 一元操作符對單個目標(比如-a)進行操作。一元字首操作符立即出現在它們的目標(比如!b)之前,一元后綴操作符立即出現在它們的目標(比如c!)之後。
  • 二元操作符對兩個目標(例如2 + 3)進行操作,並且是中綴,因為它們出現在兩個目標之間。
  • 三元運運算元對三個目標進行操作。和C一樣,Swift只有一個三元運運算元,三元條件運運算元(a ? b : c)。

操作符影響的值是運算元。在表示式1 + 2中,+符號是一個二元運運算元,它的兩個運算元是值1和2。

2 賦值運運算元

賦值操作符(a = b)初始化或更新a的值為b:

let b = 10
var a = 5
a = b
// a is now equal to 10
複製程式碼

如果賦值的右邊是一個有多個值的元組,那麼它的元素可以一次分解為多個常量或變數:

let (x,y) = (1,2)
// x is equal to 1,and y is equal to 2
複製程式碼

與C和Objective-C中的賦值操作符不同,Swift中的賦值操作符本身不返回值。以下陳述無效:

if x = y {
    // This is not valid,because x = y does not return a value.
}
複製程式碼

該特性防止在實際使用equal to操作符(==)時意外使用賦值操作符(=)。通過設定if x = y無效,Swift可以幫助您避免程式碼中出現這類錯誤。

3 算術運運算元

針對數值型別,Swift提供了四種基本的算術運運算元:

  • 加法(+)
  • 減法(-)
  • 乘法 (*)
  • 除法 (/)
1 + 2       // equals 3
5 - 3       // equals 2
2 * 3       // equals 6
10.0 / 2.5  // equals 4.0
複製程式碼

與C和Objective-C中的算術運運算元不同,Swift算術運運算元預設不允許值溢位。您可以選擇使用Swift的溢位操作符(如a &+ b)來計算溢位行為的值。請參閱溢位操作符

字串連線也支援加法運運算元:

"hello," + "world"  // equals "hello,world"
複製程式碼

3.1 餘數操作符

餘數運運算元(a % b)計算出a中可以容納多少個b的倍數,並返回剩餘的值(稱為餘數)。

注意 餘數運運算元(%)在其他語言中也稱為模運運算元。但是,它在負數中的表現意味著,嚴格地說,它是一個餘數而不是模運算。

下面是餘數運運算元的工作原理。要計算9 % 4,你首先要算出9能裝下多少個4s:

../_images/remainderInteger_2x.png

可以在9中放入兩個4s,餘數為1(用橙色表示)。

在Swift中可以這樣寫:

9 % 4    // equals 1
複製程式碼

為了確定a % b的答案,%運運算元計算以下等式並返回餘數作為輸出:

a = (b x some multiplier) + remainder
複製程式碼

some multiplier是a中b的最大倍數。

將9和4插入到這個方程,得到:

9 = (4 x 2) + 1
複製程式碼

計算a的負值的餘數時採用相同的方法:

-9 % 4   // equals -1
複製程式碼

將-9和4插入方程,得到:

-9 = (4 x -2) + -1
複製程式碼

餘數為-1。

當b為負值時,b的符號被忽略。這意味著a % b和a % -b總是給出相同的答案。

3.2 一元減(-)操作符

數字值的符號可以通過字首-來進行切換,也就是一元減運運算元:

let three = 3
let minusThree = -three       // minusThree equals -3
let plusThree = -minusThree   // plusThree equals 3,or "minus minus three"
複製程式碼

一元減運運算元(-)直接放在它所操作的值前面,沒有任何空格。

3.3 一元加(+)操作符

一元加號運運算元(+)只返回它所操作的值,沒有任何變化:

let minusSix = -6
let alsoMinusSix = +minusSix  // alsoMinusSix equals -6
複製程式碼

雖然一元加號運運算元實際上沒有任何作用,但是您可以在程式碼中使用它來為正數提供對稱,同時也可以使用一元減號運運算元來為負數提供對稱。

4 複合賦值操作符

像C一樣,Swift提供了將賦值(=)與另一個操作組合起來的複合賦值操作符。一個例子是加法賦值操作符(+=):

var a = 1
a += 2
// a is now equal to 3
複製程式碼

表示式a += 2是a = a + 2的簡寫。有效地,加法和賦值被合併到一個運運算元中,同時執行兩個任務。

注意 複合賦值操作符不返回值。例如,你不能寫b = a += 2。

有關Swift標準庫提供的操作符的資訊,請參見操作符宣告

5 比較運運算元

Swift支援所有標準C比較運運算元:

  • 等於(a == b)
  • 不等於(a != b)
  • 大於(a > b)
  • 小於(a < b)
  • 大於等於(a >= b)
  • 小於等於(a <= b)

注意 Swift還提供了兩個身份操作符(===和!==),用於測試兩個物件引用是否都引用同一個物件例項。有關更多資訊,請參見標識操作符

每個比較運運算元都返回一個Bool值來表示語句是否為真:

1 == 1   // true because 1 is equal to 1
2 != 1   // true because 2 is not equal to 1
2 > 1    // true because 2 is greater than 1
1 < 2    // true because 1 is less than 2
1 >= 1   // true because 1 is greater than or equal to 1
2 <= 1   // false because 2 is not less than or equal to 1
複製程式碼

比較運運算元常用於條件語句中,如if語句:

let name = "world"
if name == "world" {
    print("hello,world")
} else {
    print("I'm sorry \(name),but I don't recognize you")
}
// Prints "hello,world",because name is indeed equal to "world".
複製程式碼

有關If更多內容,請參閱控制流

如果兩個元組具有相同的型別和相同數量的值,則可以比較它們。元組從左到右進行比較,一次一個值,直到比較發現兩個不相等的值為止。比較這兩個值,比較的結果決定元組比較的總體結果。如果所有元素都相等,則元組本身也相等。例如:

(1,"zebra") < (2,"apple")   // true because 1 is less than 2; "zebra" and "apple" are not compared
(3,"apple") < (3,"bird")    // true because 3 is equal to 3,and "apple" is less than "bird"
(4,"dog") == (4,"dog")      // true because 4 is equal to 4,and "dog" is equal to "dog"
複製程式碼

在上面的示例中,您可以在第一行看到從左到右的比較行為。因為1小於2,所以(1,“zebra”)被認為小於(2,“apple”),而與元組中的其他值無關。“zebra”不小於“apple”並不重要,因為比較已經由元組的第一個元素決定了。但是,當元組的第一個元素相同時,將比較它們的第二個元素—這是在第二和第三行發生的事情。

只有當運運算元可以應用於相應元組中的每個值時,才能將元組與給定的運運算元進行比較。例如,如下面的程式碼所示,您可以比較型別(String,Int)的兩個元組,因為字串和Int值都可以使用<操作符進行比較。相反,型別的兩個元組(String、Bool)不能與<操作符進行比較,因為<操作符不能應用於Bool值。

("blue",-1) < ("purple",1)        // OK,evaluates to true
("blue",false) < ("purple",true)  // Error because < can't compare Boolean values
複製程式碼

注意 Swift標準庫包含元組比較運運算元,用於元素少於七個的元組。要比較具有7個或更多元素的元組,必須自己實現比較運運算元。

6 元條件運運算元

三元條件運運算元是一種特殊的運運算元,由三部分組成:question ?answer1 : answer2。這是一個計算兩個表示式中的一個的捷徑,基於問題是真的還是假的。如果question為真,它計算answer1並返回它的值;否則,它將計算answer2並返回其值。

三元條件運運算元是以下程式碼的簡寫:

if question {
    answer1
} else {
    answer2
}
複製程式碼

下面是一個示例,它計算錶行的高度。如果行有標題,行高應該比內容高50點,如果行沒有標題,行高20點:

let contentHeight = 40
let hasHeader = true
let rowHeight = contentHeight + (hasHeader ? 50 : 20)
// rowHeight is equal to 90
複製程式碼

上面程式碼是下面程式碼的簡寫:

let contentHeight = 40
let hasHeader = true
let rowHeight: Int
if hasHeader {
    rowHeight = contentHeight + 50
} else {
    rowHeight = contentHeight + 20
}
// rowHeight is equal to 90
複製程式碼

第一個示例使用了三元條件運運算元,這意味著可以在一行程式碼中將rowh8設定為正確的值,這比第二個示例中使用的程式碼更簡潔。

三元條件運運算元提供了一種有效的簡寫方式來決定兩個表示式中的哪一個要考慮。但是,使用三元條件運運算元時要小心。如果過度使用,它的簡潔性會導致難以閱讀的程式碼。避免將三元條件運運算元的多個例項組合成一個複合語句。

7 Nil-Coalescing操作符( ??操作符 )

nil-coalescing操作符(a ?? b)如果一個可選的a包含一個值,則展開它;如果a為nil,則返回一個預設值b。表示式a始終是可選型別。表示式b必須匹配儲存在a中的型別。

Nil-Coalescing操作符是下面程式碼的簡寫:

a != nil ? a! : b
複製程式碼

上面的程式碼使用三元條件運運算元和強制展開(a!),當a不是nil時訪問包裝在a中的值,否則返回b。nil-coalescing操作符提供了一種更優雅的方式,以簡潔和可讀的形式封裝這種條件檢查和展開。

注意 如果a的值是非nil,那麼b的值就不會被計算。這就是所謂的短路評估。

下面的例子使用了nil-coalescing操作符來選擇預設的顏色名稱和可選的使用者定義的顏色名稱:

let defaultColorName = "red"
var userDefinedColorName: String?   // defaults to nil

var colorNameToUse = userDefinedColorName ?? defaultColorName
// userDefinedColorName is nil,so colorNameToUse is set to the default of "red"
複製程式碼

userDefinedColorName變數被定義為一個可選字串,預設值為nil。因為userDefinedColorName是可選型別,所以可以使用nil-coalescing操作符來考慮它的值。在上面的示例中,操作符用於確定名為colorNameToUse的字串變數的初始值。因為userDefinedColorName是nil,表示式userDefinedColorName ??defaultColorName返回defaultColorName的值,或者“red”。

如果你給userDefinedColorName分配一個非nil值,並再次執行nl -coalescing操作符檢查,userDefinedColorName內的值將被使用,而不是預設值:

userDefinedColorName = "green"
colorNameToUse = userDefinedColorName ?? defaultColorName
// userDefinedColorName is not nil,so colorNameToUse is set to "green"
複製程式碼

8 範圍操作符

Swift包括幾個範圍操作符,它們是表示值範圍的快捷方式。

8.1 封閉範圍運運算元 ( ... 操作符 )

閉值域運算(a…b)定義了從a到b的值域,包括a和b的值。a的值不能大於b。

閉合範圍運運算元在迭代一個範圍時非常有用,在這個範圍內你需要使用所有的值,例如forin迴圈:

for index in 1...5 {
    print("\(index) times 5 is \(index * 5)")
}
// 1 times 5 is 5
// 2 times 5 is 10
// 3 times 5 is 15
// 4 times 5 is 20
// 5 times 5 is 25
複製程式碼

關於更多for-in迴圈,參閱控制流

8.2 半開範圍操作符( ..< 操作符)

半開區間運運算元(a..<b)定義了從a到b的範圍,但不包括b。之所以稱之為半開區間,是因為它包含了第一個值,但沒有包含最終值。與封閉範圍操作符一樣,a的值不能大於b。如果a的值等於b,那麼結果範圍將為空。

當你處理基於0的列表(比如陣列)時,半開的範圍特別有用,這裡有用的是計算列表的長度(但不包括):

let names = ["Anna","Alex","Brian","Jack"]
let count = names.count
for i in 0..<count {
    print("Person \(i + 1) is called \(names[i])")
}
// Person 1 is called Anna
// Person 2 is called Alex
// Person 3 is called Brian
// Person 4 is called Jack
複製程式碼

注意,陣列包含4個項,但是0..<count只計算到3(陣列中最後一項的索引),因為它是半開放的範圍。有關陣列的更多資訊,請參見陣列

8.3 單邊值域

對於在一個方向上儘可能連續的範圍,封閉範圍操作符有另一種形式—例如,包含陣列從索引2到陣列末尾的所有元素的範圍。在這些情況下,可以忽略範圍操作符一側的值。這種值域稱為單邊值域,因為運運算元只有一邊有值。例如:

for name in names[2...] {
    print(name)
}
// Brian
// Jack

for name in names[...2] {
    print(name)
}
// Anna
// Alex
// Brian
複製程式碼

半開式值域運運算元也有一個單邊形式,只有它的最終值。就像在兩邊都包含值一樣,最終值也不屬於範圍內。例如:

for name in names[..<2] {
    print(name)
}
// Anna
// Alex
複製程式碼

單邊值域可以在其他上下文中使用,而不僅僅是下標。您不能遍歷遺漏第一個值的單邊值域,因為不清楚迭代應該從哪裡開始。您可以迭代一個單邊的值域,省略其最終值;但是,由於範圍是無限延續的,所以請確保為迴圈添加了一個顯式的結束條件。還可以檢查單邊值域是否包含特定值,如下面的程式碼所示。

let range = ...5
range.contains(7)   // false
range.contains(4)   // true
range.contains(-1)  // true
複製程式碼

9 邏輯運運算元

邏輯運運算元修改或組合布林邏輯值true和false。Swift支援基於c語言的三種標準邏輯運運算元:

  • 邏輯 非 (!a)
  • 邏輯 與 (a && b)
  • 邏輯 或 (a || b)

9.1 邏輯非運運算元

邏輯非操作符(!a)反轉布林值,使真變為假,假變為真。

邏輯非操作符是一個字首操作符,它出現在它所操作的值的前面,沒有任何空格。可以理解為“非 a”,如下例所示:

let allowedEntry = false
if !allowedEntry {
    print("ACCESS DENIED")
}
// Prints "ACCESS DENIED"
複製程式碼

“if !allowedEntry”可以理解為“if not allowed entry”。後面的行只在“not allowed entry”為真時執行;也就是說,如果allowedEntry為false。

與本例一樣,謹慎選擇布林常量和變數名有助於保持程式碼可讀性和簡潔,同時避免雙重否定或邏輯語句混亂。

9.2 邏輯與運運算元

邏輯和運運算元(a && b)建立邏輯表示式,其中兩個值必須為真,整個表示式也為真。

如果任一值為假,則整個表示式也為假。事實上,如果第一個值為假,第二個值甚至不會計算,因為它不可能使整個表示式等於真。這就是所謂的短路評估。

這個例子考慮了兩個Bool值,只有當兩個值都為真時才允許訪問:

let enteredDoorCode = true
let passedRetinaScan = false
if enteredDoorCode && passedRetinaScan {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Prints "ACCESS DENIED"
複製程式碼

9.3 邏輯或運運算元

邏輯或操作符(|| b)是由兩個相鄰管道字元組成的中綴操作符。您可以使用它來建立邏輯表示式,其中兩個值中只有一個必須為真才能使整個表示式為真。

與上面的邏輯和運運算元一樣,邏輯或運運算元使用短路求值來考慮其表示式。如果邏輯或表示式的左邊為真,則不計算右邊的值,因為它不能改變整個表示式的結果。

在下例中,第一個Bool值(hasDoorKey)為假,但第二個值(knowsOverridePassword)為真。因為一個值為真,整個表示式的計算結果也為真,因此允許訪問:

let hasDoorKey = false
let knowsOverridePassword = true
if hasDoorKey || knowsOverridePassword {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Prints "Welcome!"
複製程式碼

9.4 組合的邏輯運運算元

您可以組合多個邏輯運運算元來建立更長的複合表示式:

if enteredDoorCode && passedRetinaScan || hasDoorKey || knowsOverridePassword {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Prints "Welcome!"
複製程式碼

這個示例使用多個&&和||操作符建立一個更長的複合表示式。但是,&&和||操作符仍然只對兩個值進行操作,因此這實際上是三個連線在一起的較小的表示式。這個例子可以理解為:

如果我們輸入了正確的門碼並且通過了視網膜掃描,或者如果我們有一個有效的門鑰匙,或者如果我們知道緊急控制密碼,那麼就允許進入。

根據enteredDoorCode、passedRetinaScan和hasDoorKey的值,前兩個子表示式為false。但是,緊急覆蓋密碼是已知的,因此整個複合表示式的計算結果仍然為true。

注意 Swift邏輯運運算元&&和||是左關聯的,這意味著包含多個邏輯運運算元的複合表示式首先計算最左邊的子表示式。

9.5 用括號分隔多個邏輯運運算元

有時,如果不是嚴格需要括號,那麼包含括號是很有用的,這樣可以使複雜表示式的意圖更容易理解。在上面的door access示例中,在複合表示式的第一部分周圍新增括號以明確其意圖是很有用的:

if (enteredDoorCode && passedRetinaScan) || hasDoorKey || knowsOverridePassword {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Prints "Welcome!"
複製程式碼

括號清楚地表明前兩個值被視為整個邏輯中單獨可能的狀態的一部分。複合表示式的輸出沒有變化,但總體意圖對讀者更清晰。可讀性總是比簡潔更重要;使用括號來幫助明確你的意圖。

總結

這一章節的內容比較簡單,一些運運算元操作基本上和C、OC上的一樣,不過在Swift上也有它特有的一些運運算元,可以簡化程式碼,如下所示:

  • ?? 操作符
  • 封閉範圍操作符(...) 、半開範圍操作符(..<) 和單邊值域

具體的作用,可以翻看上面的內容找到答案。

最後,喜歡的朋友可以打個star哦!這樣我才更有動力繼續下去,嘎嘎嘎~

上一章節:基礎

下一章節:字串和字元

參考檔案:Swift - Basic Operators