前言
流程控制語句是用來控制程序中各語句執行順序的語句,可以把語句組合成能完成一定功能的小邏輯模塊。
控制語句分為三類:順序、選擇和循環。
順序結構:代表“先執行a,再執行b”的邏輯。
選擇結構:代表“如果…,則…”的邏輯。
循環結構:代表“如果…,則重復執行…”的邏輯。
實際上,任何軟件和程序,小到一個練習,大到一個操作系統,本質上都是由“變量、選擇語句、循環語句”組成。
這三種基本邏輯結構是相互支撐的,它們共同構成了算法的基本結構,無論怎樣復雜的邏輯結構,都可以通過它們來表達。
if-then
它告訴你要只有 if 后面是 true 時才執行特定的代碼。
1
2
3
4
5
6
7
|
void applyBrakes() { // the "if" clause: bicycle must be moving if (isMoving){ // the "then" clause: decrease current speed currentSpeed--; } } |
如果 if 后面是 false, 則跳到 if-then 語句后面。語句可以省略中括號,但在編碼規范里面不推薦使用,如:
1
2
3
4
5
|
void applyBrakes() { // same as above, but without braces if (isMoving) currentSpeed--; } |
if-then-else
該語句是在 if 后面是 false 時,提供了第二個執行路徑。
1
2
3
4
5
6
7
|
void applyBrakes() { if (isMoving) { currentSpeed--; } else { System.err.println( "The bicycle has already stopped!" ); } } |
下面是一個完整的例子:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
class IfElseDemo { /** * @param args */ public static void main(String[] args) { int testscore = 76 ; char grade; if (testscore >= 90 ) { grade = 'A' ; } else if (testscore >= 80 ) { grade = 'B' ; } else if (testscore >= 70 ) { grade = 'C' ; } else if (testscore >= 60 ) { grade = 'D' ; } else { grade = 'F' ; } System.out.println( "Grade = " + grade); } } |
輸出為:Grade = C
switch
switch 語句可以有許多可能的執行路徑??梢允褂?byte, short, char, 和 int 基本數據類型,也可以是枚舉類型(enumerated types)、String 以及少量的原始類型的包裝類 Character, Byte, Short, 和 Integer。
下面是一個 SwitchDemo 例子:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
|
class SwitchDemo { /** * @param args */ public static void main(String[] args) { int month = 8 ; String monthString; switch (month) { case 1 : monthString = "January" ; break ; case 2 : monthString = "February" ; break ; case 3 : monthString = "March" ; break ; case 4 : monthString = "April" ; break ; case 5 : monthString = "May" ; break ; case 6 : monthString = "June" ; break ; case 7 : monthString = "July" ; break ; case 8 : monthString = "August" ; break ; case 9 : monthString = "September" ; break ; case 10 : monthString = "October" ; break ; case 11 : monthString = "November" ; break ; case 12 : monthString = "December" ; break ; default : monthString = "Invalid month" ; break ; } System.out.println(monthString); } } |
break 語句是為了防止 fall through。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
|
class SwitchDemoFallThrough { /** * @param args */ public static void main(String[] args) { java.util.ArrayList<String> futureMonths = new java.util.ArrayList<String>(); int month = 8 ; switch (month) { case 1 : futureMonths.add( "January" ); case 2 : futureMonths.add( "February" ); case 3 : futureMonths.add( "March" ); case 4 : futureMonths.add( "April" ); case 5 : futureMonths.add( "May" ); case 6 : futureMonths.add( "June" ); case 7 : futureMonths.add( "July" ); case 8 : futureMonths.add( "August" ); case 9 : futureMonths.add( "September" ); case 10 : futureMonths.add( "October" ); case 11 : futureMonths.add( "November" ); case 12 : futureMonths.add( "December" ); break ; default : break ; } if (futureMonths.isEmpty()) { System.out.println( "Invalid month number" ); } else { for (String monthName : futureMonths) { System.out.println(monthName); } } } } |
輸出為:
August
September
October
November
December
技術上來說,最后一個 break 并不是必須,因為流程跳出 switch 語句。但仍然推薦使用 break ,主要修改代碼就會更加簡單和防止出錯。default 處理了所有不明確值的情況。
下面例子展示了一個局域多個 case 的情況。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
|
class SwitchDemo2 { /** * @param args */ public static void main(String[] args) { int month = 2 ; int year = 2000 ; int numDays = 0 ; switch (month) { case 1 : case 3 : case 5 : case 7 : case 8 : case 10 : case 12 : numDays = 31 ; break ; case 4 : case 6 : case 9 : case 11 : numDays = 30 ; break ; case 2 : if (((year % 4 == 0 ) && !(year % 100 == 0 )) || (year % 400 == 0 )) numDays = 29 ; else numDays = 28 ; break ; default : System.out.println( "Invalid month." ); break ; } System.out.println( "Number of Days = " + numDays); } } |
輸出為:Number of Days = 29
使用 String
Java SE 7 開始,可以在 switch 語句里面使用 String,下面是一個例子
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
|
class StringSwitchDemo { public static int getMonthNumber(String month) { int monthNumber = 0 ; if (month == null ) { return monthNumber; } switch (month.toLowerCase()) { case "january" : monthNumber = 1 ; break ; case "february" : monthNumber = 2 ; break ; case "march" : monthNumber = 3 ; break ; case "april" : monthNumber = 4 ; break ; case "may" : monthNumber = 5 ; break ; case "june" : monthNumber = 6 ; break ; case "july" : monthNumber = 7 ; break ; case "august" : monthNumber = 8 ; break ; case "september" : monthNumber = 9 ; break ; case "october" : monthNumber = 10 ; break ; case "november" : monthNumber = 11 ; break ; case "december" : monthNumber = 12 ; break ; default : monthNumber = 0 ; break ; } return monthNumber; } public static void main(String[] args) { String month = "August" ; int returnedMonthNumber = StringSwitchDemo.getMonthNumber(month); if (returnedMonthNumber == 0 ) { System.out.println( "Invalid month" ); } else { System.out.println(returnedMonthNumber); } } } |
輸出為:8
注:switch 語句表達式中不能有 null。
while
while 語句在判斷條件是 true 時執行語句塊。語法如下:
1
2
3
|
while (expression) { statement(s) } |
while 語句計算的表達式,必須返回 boolean 值。如果表達式計算為 true,while 語句執行 while 塊的所有語句。while 語句繼續測試表達式,然后執行它的塊,直到表達式計算為 false。完整的例子:
1
2
3
4
5
6
7
8
9
10
11
12
13
|
class WhileDemo { /** * @param args */ public static void main(String[] args) { int count = 1 ; while (count < 11 ) { System.out.println( "Count is: " + count); count++; } } } |
用 while 語句實現一個無限循環:
1
2
3
|
while ( true ){ // your code goes here } |
do-while
語法如下:
1
2
3
|
do { statement(s) } while (expression); |
do-while 語句和 while 語句的區別是,do-while 計算它的表達式是在循環的底部,而不是頂部。所以,do 塊的語句,至少會執行一次,如 DoWhileDemo 程序所示:
1
2
3
4
5
6
7
8
9
10
11
12
13
|
class DoWhileDemo { /** * @param args */ public static void main(String[] args) { int count = 1 ; do { System.out.println( "Count is: " + count); count++; } while (count < 11 ); } } |
輸出為:
Count is: 1
Count is: 2
Count is: 3
Count is: 4
Count is: 5
Count is: 6
Count is: 7
Count is: 8
Count is: 9
Count is: 10
for
for 語句提供了一個緊湊的方式來遍歷一個范圍值。程序經常引用為"for 循環",因為它反復循環,直到滿足特定的條件。for 語句的通常形式,表述如下:
1
2
3
4
|
for (initialization; termination; increment) { statement(s) } |
使 for 語句時要注意:
- initialization 初始化循環;它執行一次作為循環的開始。
- 當 termination 計算為 false,循環結束。
- increment 會在循環的每次迭代執行;該表達式可以接受遞增或者遞減的值
1
2
3
4
5
6
7
8
9
10
11
12
|
class ForDemo { /** * @param args */ public static void main(String[] args) { for ( int i= 1 ; i< 11 ; i++){ System.out.println( "Count is: " + i); } } } |
輸出為:
Count is: 1
Count is: 2
Count is: 3
Count is: 4
Count is: 5
Count is: 6
Count is: 7
Count is: 8
Count is: 9
Count is: 10
注意:代碼在 initialization 聲明變量。該變量的存活范圍,從它的聲明到 for 語句的塊的結束。所以,它可以用在 termination 和 increment。如果控制 for 語句的變量,不需要在循環外部使用,最好是在 initialization 聲明。經常使用 i,j,k 經常用來控制 for 循環。在 initialization 聲明他們,可以限制他們的生命周期,減少錯誤。
for 循環的三個表達式都是可選的,一個無限循環,可以這么寫:
1
2
3
4
5
|
// infinite loop for ( ; ; ) { // your code goes here } |
for 語句還可以用來迭代 集合(Collections) 和 數組(arrays),這個形式有時被稱為增強的 for 語句( enhanced for ),可以用來讓你的循環更加緊湊,易于閱讀。為了說明這一點,考慮下面的數組:
1
|
int [] numbers = { 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 }; |
使用 增強的 for 語句來循環數組
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
class EnhancedForDemo { /** * @param args */ public static void main(String[] args) { int [] numbers = { 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 }; for ( int item : numbers) { System.out.println( "Count is: " + item); } } } |
輸出:
Count is: 1
Count is: 2
Count is: 3
Count is: 4
Count is: 5
Count is: 6
Count is: 7
Count is: 8
Count is: 9
Count is: 10
盡可能使用這種形式的 for 替代傳統的 for 形式。
break
break 語句有兩種形式:標簽和非標簽。在前面的 switch 語句,看到的 break 語句就是非標簽形式。可以使用非標簽 break 用來結束 for,while,do-while 循環,如下面的 BreakDemo 程序:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
|
class BreakDemo { /** * @param args */ public static void main(String[] args) { int [] arrayOfInts = { 32 , 87 , 3 , 589 , 12 , 1076 , 2000 , 8 , 622 , 127 }; int searchfor = 12 ; int i; boolean foundIt = false ; for (i = 0 ; i < arrayOfInts.length; i++) { if (arrayOfInts[i] == searchfor) { foundIt = true ; break ; } } if (foundIt) { System.out.println( "Found " + searchfor + " at index " + i); } else { System.out.println(searchfor + " not in the array" ); } } } |
這個程序在數組終查找數字12。break 語句,當找到值時,結束 for 循環??刂屏骶吞D到 for 循環后面的語句。程序輸出是:
Found 12 at index 4
無標簽 break 語句結束最里面的 switch,for,while,do-while 語句。而標簽break 結束最外面的語句。接下來的程序,BreakWithLabelDemo,類似前面的程序,但使用嵌套循環在二維數組里尋找一個值。但值找到后,標簽 break 語句結束最外面的 for 循環(標簽為"search"):
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
class BreakWithLabelDemo { /** * @param args */ public static void main(String[] args) { int [][] arrayOfInts = { { 32 , 87 , 3 , 589 }, { 12 , 1076 , 2000 , 8 }, { 622 , 127 , 77 , 955 } }; int searchfor = 12 ; int i; int j = 0 ; boolean foundIt = false ; search: for (i = 0 ; i < arrayOfInts.length; i++) { for (j = 0 ; j < arrayOfInts[i].length; j++) { if (arrayOfInts[i][j] == searchfor) { foundIt = true ; break search; } } } if (foundIt) { System.out.println( "Found " + searchfor + " at " + i + ", " + j); } else { System.out.println(searchfor + " not in the array" ); } } } |
程序輸出是:
Found 12 at 1, 0
break 語句結束標簽語句,它不是傳送控制流到標簽處??刂屏鱾魉偷骄o隨標記(終止)聲明。
注: Java 沒有類似于 C 語言的 goto 語句,但帶標簽的 break 語句,實現了類似的效果。
continue
continue 語句忽略 for,while,do-while 的當前迭代。非標簽模式,忽略最里面的循環體,然后計算循環控制的 boolean 表達式。接下來的程序,ContinueDemo,通過一個字符串的步驟,計算字母“p”出現的次數。如果當前字符不是 p,continue 語句跳過循環的其他代碼,然后處理下一個字符。如果當前字符是 p,程序自增字符數。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
class ContinueDemo { /** * @param args */ public static void main(String[] args) { String searchMe = "peter piper picked a " + "peck of pickled peppers" ; int max = searchMe.length(); int numPs = 0 ; for ( int i = 0 ; i < max; i++) { // interested only in p's if (searchMe.charAt(i) != 'p' ) continue ; // process p's numPs++; } System.out.println( "Found " + numPs + " p's in the string." ); } } |
程序輸出:
Found 9 p's in the string
為了更清晰看效果,嘗試去掉 continue 語句,重新編譯。再跑程序,count 將是錯誤的,輸出是 35,而不是 9.
帶標簽的 continue 語句忽略標簽標記的外層循環的當前迭代。下面的程序例子,ContinueWithLabelDemo,使用嵌套循環在字符傳的字串中搜索字串。需要兩個嵌套循環:一個迭代字串,一個迭代正在被搜索的字串。下面的程序ContinueWithLabelDemo,使用 continue 的標簽形式,忽略最外層的循環。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
class ContinueWithLabelDemo { /** * @param args */ public static void main(String[] args) { String searchMe = "Look for a substring in me" ; String substring = "sub" ; boolean foundIt = false ; int max = searchMe.length() - substring.length(); test: for ( int i = 0 ; i <= max; i++) { int n = substring.length(); int j = i; int k = 0 ; while (n-- != 0 ) { if (searchMe.charAt(j++) != substring.charAt(k++)) { continue test; } } foundIt = true ; break test; } System.out.println(foundIt ? "Found it" : "Didn't find it" ); } } |
這里是程序輸出:
Found it
return
最后的分支語句是 return 語句。return 語句從當前方法退出,控制流返回到方法調用處。return 語句有兩種形式:一個是返回值,一個是不返回值。為了返回一個值,簡單在 return 關鍵字后面把值放進去(或者放一個表達式計算)。
1
|
return ++count; |
return 的值的數據類型,必須和方法聲明的返回值的類型符合。當方法聲明為 void,使用下面形式的 return 不需要返回值。
1
|
return ; |
總結
到此這篇關于Java中控制流程語句的文章就介紹到這了,更多相關Java控制流程語句內容請搜索服務器之家以前的文章或繼續瀏覽下面的相關文章希望大家以后多多支持服務器之家!
原文鏈接:https://juejin.cn/post/7021026073345261598