golang 流程控制
阿新 • • 發佈:2020-08-12
目錄
前言
- 不做文字的搬運工,多做靈感性記錄
- 這是平時學習總結的地方,用做知識庫
- 平時看到其他文章的相關知識,也會增加到這裡
- 隨著學習深入,會進行知識拆分和彙總,所以文章會隨時更新
- 參考的文章過多、很雜很亂,所以參考會寫不全,見諒
流程控制
主要是三大流程控制流程控制語句
1)順序控制
2)分支控制
3)迴圈控制
1.順序控制
程式從上到下逐行地執行,中間沒有任何判斷和跳轉。
-
注意
-
Golang中定義變數時採用合法的前向引用。
就是說你使用變數就需要提前宣告它
-
2.分支語句
1.形式
- 單分支
- 雙分支
- 多分支
2.單分支控制 if
基本語法
if 條件表示式 {
執行程式碼塊
}
條件表示式為true時,就會執行{}的程式碼,注意{}是必須有的,就算你值寫一行程式碼
// golang支援在if中直接定義一個變數
if age := 20;age > 18{
...
}
3.雙分支語句 if
if 條件表示式 {
執行程式碼塊 1
}else{
執行程式碼塊 2
}
// 注意
1.條件表示式為true時,就會執行程式碼塊1,否則就執行程式碼塊2,注意{}是必須有的
2.雙分支只會執行其中的一個分支
4.多分支控制 if
if 條件表示式 {
執行程式碼塊1
}else if 條件表示式{
執行程式碼塊2
}else if 條件表示式{
執行程式碼塊3
}else{
執行程式碼塊 n
}
// 注意
else不是必須的,但多分支只能執行一個執行入口
5.巢狀分支
在一個分支結構中又完整的嵌套了另一個完整的分支結構,裡面的分支的結構稱為內層分支,外面的分支結構稱為外層分支。巢狀分支不宜過多,建議控制在3層內。
6.switch分支控制
- switch語句用於基於不同條件執行不同動作,每一個case分支都是唯一的,從上到下逐一測試,直到匹配為止。
- 匹配項後面也不需要再加break
switch 表示式{
case 表示式1,表示式2,...:
語句塊1
case 表示式3,表示式4,...:
語句塊2
default:
語句塊3
}
// 注意
1.先執行switch的表示式得到值。然後執行case的語句,進行比較,遇到相等的,就比配到,執行對應的case的語句塊,然後退出switch,如果沒有匹配成功,就會執行default語句
2.case後的表示式可以有多個,用逗號隔開
3.switch 後面也可以不帶表示式,直接跟上(:)類似 if - case 分支來使用
switch:{}
4.switch 後面也可以直接宣告/定義一個變數,以分號結尾(不推薦)
switch grade:=90;{}
5.switch穿透-fallthough,
如果在case語句塊後增加fallthrough,會繼續執行下一個case,
var num int = 20
switch num{
case 10:
fmt.Print('ok')
fallthrough //預設只能穿透一層,執行case 30
case 30:
fmt.Print('1')
// case不需寫break,預設情況下執行case語句以後,就跳出switch控制語句
break
default: // 不是必須的,
fmt.Print('2')
}
6.type-switch:
// 判斷某個interface 變數中實際指向的變數型別
var x interface{}
var y = 10.0
x = y
switch i:=x.(type){
case nil:
fmt.Print('x的型別是:%T',i)
case int:
fmt.Print('x的型別是整型')
}
7.switch 和 if 區別
-
如果判斷的具體數值不多,而且符合整數、浮點數、字元、字串這幾種型別。建議使用swtich語句,簡潔高效。
-
其他情況:對區間判斷和結果為bool型別的判斷,使用if, if的使用範圍更廣。
3.迴圈結構
- golang中沒有while和do..while的語法,需要通過for迴圈實現
1.for迴圈結構
for 迴圈變數初始化 ;迴圈條件 ; 迴圈變數迭代{
迴圈執行語句(語句)
}
// 注意省略情況
1. 省略初始化迴圈變數、迴圈變數迭代: //相當於while迴圈
for i > 10{}
迴圈變數初始化
說明:1.此for迴圈是一個無限迴圈
2.break就是來跳出for語句
2.全部省略 // 無限迴圈
1.保留分號
for ; ;{
迴圈執行語句
break
}
2.不保留分號
// 實現 while
// 實現 do - while
for{
迴圈執行語句
break
}
2.實現while 迴圈
for{
if 迴圈條件表示式{
break //跳出for迴圈
}
迴圈操作(語句)
迴圈變數迭代
}
3.實現 do - while
迴圈變數初始化
for{
迴圈操作(語句)
迴圈變數的迭代
if 迴圈條件表示式{
break //跳出for迴圈
}
}
1.先執行,再判斷,因此至少執行一次
2.迴圈條件成立後,就會執行break,跳出for 迴圈,結束迴圈
4.構成
1.初始語句
開始迴圈執行的語句, 第一次迴圈前執行的語句,一般使用初始語句執行變數初始化,如果變數在此處被宣告,其作用域將被侷限在這個 for 的範圍內。
初始語句可以被忽略,但是初始語句之後的分號必須要寫,
2.條件表示式
控制是否迴圈的開關, 每次迴圈開始前都會計算條件表示式,
表示式為 true :則迴圈繼續,
表示式為False :結束迴圈
表示式忽略 :後預設形成無限迴圈。
3.結束語句
在結束每次迴圈前執行的語句,如果迴圈被 break、goto、return、panic 等語句強制退出,結束語句不會被執行。
5.多重迴圈控制
- 一個迴圈放在另一個迴圈體內,就形成了巢狀迴圈,建議一般使用兩層,最多不適用三層
- 實質就是內層迴圈的迴圈條件為false時,才會跳出內層迴圈,才結束外層的 當次 迴圈
- 外層迴圈m次,內層迴圈n次,則內層迴圈體需要執行 m * n次
- 編譯後先易後難,將一個複雜的問題分解為簡單的問題,
6.跳出迴圈
1. break
- 一般都是用來跳出
for
或switch
語句。在 Go 中也可以在select
語句中使用break
。 - 跳出 當前(最近) 的 for 迴圈或者switch語句
- 跳出標籤
// break後面可以指定標籤,跳出標籤對應的for迴圈
// 為不帶標籤的break只能終止最內層(innermost)的迴圈,如果像終止外部的迴圈,就得用標籤了:
lable 2:
for i := 0;i < 4; i++{
for j := 0;j < 4;j++{ //設定一個lable1
if j == 2{
break lable2 //跳出lable2下面對應的for迴圈
}
}
}
- 語句不能跨越函式邊界。
// 跨越邊界會報錯 break is not in a loop, switch, or select
2. fallthrough
2.contine
-
跳出本次迴圈,執行下一次迴圈
-
可以通過標籤指明要跳過的哪一層迴圈,調到標籤對應的 for 迴圈處
here: for i:=0;i<4;i++{ for j:=1;j<4;j++{ if j==2{ continue here } fmt.Print("i=",i,"j=",j) } } /* i= 0 j= 1 i= 1 j= 1 i= 2 j= 1 i= 3 j= 1 */
3.goto
- 可以無條件跳到程式中指定的行,接著往下執行
- goto語句通常與條件語句配合使用。可用來實現條件轉移,跳出迴圈體等功能。
- 不建議使用,以免造成程式流程的混亂,使理解和除錯程式都產生困難
if n > 20{
goto lable2
}
lable2:
4.return
-
如果return是在普通的函式,則表示跳出當前所在的方法或函式,即不再執行函式中return後面程式碼,也可以理解成終止函式
-
如果return是在main函式,表示終止main函式,也就是說終止程式。
-
1、無返回型別
- return語句不能返回任何值。
-
2、有返回型別
-
返回值可以顯示地寫在return的後面,每個表示式必須是單值的
func simpleF() int { return 2 } func complexF1() (re float64, im float64) { return -7.0, -4.0 }
-
return語句中的表示式列表可以是對返回多隻函式的呼叫
func complexF2() (re float64, im float64) { return complexF1() }
-
如果函式的返回型別引數指定了名字,則 return 可以返回空。這些返回型別引數就像本地變數一樣。
// 所有的結果值在函式的開始時都被初始化為它們的零值 func complexF3() (re float64, im float64) { re = 7.0 im = 4.0 return // 沒有引數的 return 語句返回各個返回變數的當前值。這種用法被稱作“裸”返回。 } func (devnull) Write(p []byte) (n int, _ error) { n = len(p) return } func f(n int) (res int, err error) { if _, err := f(n-1); err != nil { return // invalid return statement: err is shadowed ,編譯器不允許返回空?? } return } // 編譯器不知道你具體會在哪裡返回,這個要執行時才能確定,所以,你最外面沒有返回,編譯器就認為你錯了,語法不通過 // 儘量不要使用 func test() error{} 這種哦最後不能裸返回,有點兒糟心
-