摘要:前言就在前幾天,語言入門到進階部分的專欄維生素語言終于完成了。表達式條件判斷部分,用于判斷循環終止。注意事項為了防止循環失去控制,禁止在循環體內修改循環變量。判斷部分的省略判斷部分恒為真死循環。
就在前幾天,C語言入門到進階部分的專欄 ——《維生素C語言》終于完成了。全文共計十八個章節并附帶三張筆試練習篇,美中不足的是,第一章和第二章是以截圖形式展現的。由于本人一開始是在有道云筆記上寫的初稿,當時想方便省事(有道云排版個人感覺確實比較美觀)就直接以截圖的形式完成了第一章和第二章。本人考慮到因為是截圖,不能復制文中出現的代碼,不方便讀者進行復制粘貼,所以我打算重新寫一下第一章和第一章的內容,并且重新進行了排版。
? C語言中,由一個分號( ;)隔開的即為一條語句。
? 這些都是語句:
( 一行里只有 ;的語句,我們稱其為 "空語句" )
int main(void) { printf("hello world!/n"); // 語句; 3 + 5; // 語句; ; // 空語句;}
? 定義: 0為假,非0即為真(比如:1是真,0是假)
? 單 if 語句演示:
int main(void) { int age = 0; scanf("%d", age); if ( age >= 18 ) printf("成年/n"); return 0;}
? if...else 演示:
int main(void) { int age = 0; scanf("%d", age); if ( age >= 18 ) printf("成年/n"); else printf("未成年"); return 0;}
? 多分支演示:
int main(void) { int age = 0; scanf("%d", age); if(age<18) { printf("少年/n"); } else if(age>=18 && age<30) { printf("青年/n"); } else if(age>=30 && age<50) { printf("中年/n"); } else if(age>=50 && age<120) { printf("老年/n"); } else { printf("請輸入正確的年齡/n"); } return 0;}
? 判斷一個數是否為奇數:
int main(void) { int n = 0; scanf("%d", &n); if(n % 2 == 0) { printf("不是奇數/n"); } else { printf("是奇數/n"); } return 0;}
? 如果條件成立,需要執行多條語句,應該使用代碼塊,一對大括號,就是一個代碼塊。
? 建議:無論是一行語句還是多行語句,建議都加上大括號。
? 不加大括號的隱患:懸空 else
? 下列代碼會打印 abc 嗎?
int main(void) { int a = 0; int b = 2; if ( a == 1 ) if ( b == 2 ) printf("123/n"); else printf("abc/n"); return 0;}
? 運行結果:(什么都沒打印出來)
? 解析:因為沒有大括號,else 與離它最近的一個if相結合( 即內部 if ),所以即使 else 與外部 if 相對應,也沒用。
? 訂正:加上大括號之后,可以使代碼的邏輯更加清楚!
int main(void) { int a = 0; int b = 2; if(a == 1) { if(b == 2) { printf("hehe/n"); } } else { printf("haha/n"); } return 0; }
? 運行結果: abc
代碼一:可讀性不好,但是節省空間
代碼二:可讀性強
代碼三:我們希望 hello 不被打印出來,但是事實上他打印出來了;
int main(){ int num = 0; if ( num = 5 ) { printf("hello/n"); // = 賦值 == 判斷相等; } return 0;}
? 解析:為什么會這樣呢?因為在 if 語句中 num = 5 相當于重新賦值了。
? 為了防止把一個等號寫成兩個等號,發生這樣的BUG,我們可以這么寫:
int main(){ int num = 0; if (5 == num) { printf("hehe/n"); } return 0;}
這樣寫,如果不小心寫成了 "=",運行都運行不了,可以讓自己很容易地發現問題。這是種好的代碼風格!未來如果涉及到常量和變量相比較,比較相等與否,我們不妨把變量放在雙等號的右邊,常量放在左邊,以防不小心少打一個 "=" ,導致程序出錯。
? 關于 return 0
int test() { if (1) { return 0; // 當return 0 執行了,下面的代碼都不會執行了; } printf("hehe/n"); return 1;}int main(void) { test(); return 0;}
? 介紹:switch 語句是一種多分支語句,常常用于多分支的情況。一個標準 switch 語句的組成:
① case 語句項:后面接常量表達式(類型只能是整型和枚舉類型)。
② break 語句:用來跳出 switch 語句,實際效果是把語句列表劃分為不同的部分。
③ default 子句:默認執行的語句,當所有 case 都無法與 switch 的值相匹配時執行。
? 注意事項:
1. case 和 default 后面記得加 :(冒號),而不是分號。
2. 在 switch 語句中可以出現if語句。
3. switch 后面必須是整型常量表達式。
4. 每個 switch 語句后面只能有一個 default。
5. 不一定非要加 default,也可以不加。
? 建議:
1. 在最后一個 case 語句的后面也加上一條 break 語句,以防未來增添語句項時遺漏。
2. 建議在每個 switch 中都加入 default 子句,甚至在后邊再加一個 break 都不過分。
? switch 用法演示:用戶輸入一個數字x,返回星期(eg. 1 >>> 星期一)
int main(void) { int day = 0; scanf("%d", &day); switch (day) { case 1: printf("星期一/n"); break; // 跳出switch case 2: printf("星期二/n"); break; case 3: printf("星期三/n"); break; case 4: printf("星期四/n"); break; case 5: printf("星期五/n"); break; case 6: printf("星期六/n"); break; case 7: printf("星期日/n"); break; default: // 默認執行的語句; break; } return 0;}
? 多 case 同一個結果情況演示:輸入1-5,輸出 工作日;輸入6-7,輸出休息日;其他數字返回error
int main(void) { int day = 0; scanf("%d", &day); switch (day) { case 1: case 2: case 3: case 4: case 5: printf("工作日/n"); break; case 6: case 7: printf("休息日/n"); break; // 末尾加上break是個好習慣; default: printf("輸入錯誤/n"); break; // 這里可以不加break,但是加上是個好習慣; return 0;}
? 下列代碼輸出值是多少?
int main(void) { int n = 1; int m = 2; switch(n) { case 1: m++; case 2: n++; case 3: switch(n) { case 1: n++; case 2: m++; n++; break; } case 4: m++; break; default: break; } printf("m = %d, n = %d/n", m, n); return 0;}
? 答案:m = 5, n = 3
? 解析:因為n=1,所以進入switch后執行case1的語句m++,此時m=3,由于該語句項末尾沒有break,繼續向下流到case2的語句n++,此時n=2,又沒有break,流向case3,case3中又嵌了一個switch(n),此時因n=2,執行內部switch的case2的語句m++和n++,此時m=4,n=3,后面有break,跳出內部switch,但是外部switch的case3后面依然沒有break,所以流向case4,m++,此時m=5,后面終于有break了。運行下來后的結果為 m=5,n=3。
? 定義:當滿足條件時進入循環,進入循環后,當條件不滿足時,跳出循環。
? 注意事項:while 循環條件將會比循環體多執行一次。
while 循環中,當條件表達式成立時,才會執行循環體中語句,每次執行期間,都會對循環因子進行修改(否則就成為死循環),修改完成后如果 while 條件表達式成立,繼續循環,如果不成立,循環結束。
? while死循環:表達式結果如果為非0,為真,循環就執行
int main(void) { while(1) printf("hehe/n"); return 0;}
? 運行結果如下:
? while 循環打印 1~10 的數字:
int main(void) { int i = 1; while(i<=10) { printf("%d ", i); i++; } return 0;}
? 運行結果: 1 2 3 4 5 6 7 8 9 10
? break 語句在 while 循環中的效果:
在 while 循環中,break 用于永久地終止循環。
int main(void) { int i = 1; while(i <= 10) { if(5 == i) // i=5時停止循環; break; printf("%d ", i); i++; } return 0;}
?? 運行結果:1 2 3 4
? continue 語句:
int main(){ int i = 1; while(i<=10) { if(i==5) { continue; // 跳至判斷部分; } printf("%d ", i); i++; } return 0;}
? 運行結果: 1 2 3 4(程序會一直判斷)
? getchar:
從流(stream)或鍵盤上,讀取一個字符。
返回值:如果正確,返回ASCII值;如果讀取錯誤嗎,返回 EOF(文件結束標志)。
? putchar:單純的輸出一個字符。
? getchar 使用方法演示: "輸入什么就返回什么"
int main(void) { int ch = getchar(); putchar(ch); // 輸出一個字符; return 0;}
? 運行結果:(假設輸入a)? a
? getchar 與 while 的結合: "一直從鍵盤上讀取字符的程序"
int main(void) { int ch = 0; // ctrl+z - getchar 就讀取結束; while ( (ch = getchar()) != EOF ) { putchar(ch); } return 0;}
? 如果想停止輸入,怎么辦?
? 解決方法: 輸入 ctrl + z 可以使 getchar 結束讀取。
? getchar 只打印數字:
int main(void) { int ch = 0; while( (ch=getchar()) != EOF ) { if(ch<"0" || ch>"9") { continue; // 發現不是數字,跳回判斷部分,重新getchar; } putchar(ch); } return 0;}
? 清理緩沖區:用戶輸入密碼后,讓用戶確認(Y/N)
int main(void) { char password[20] = {0}; printf("請輸入密碼:>"); scanf("%s", password); printf("請確認密碼(Y/N) :>"); int ch = getchar(); if(ch == "Y") { printf("確認成功/n"); } else { printf("確認失敗/n"); } return 0; }
? 運行結果:(假設用戶輸入了123456;Y)確認失敗
?? 為什么還沒有讓用戶確認(Y/N)就顯示確認失敗了?
? 解析:輸入函數并不是從鍵盤上讀取,而是從緩沖區中讀取內容的;鍵盤輸入123456時敲下回車鍵,此時為 “123456/n”,這時scanf將123456取走,getchar讀取到的就是“/n”了,因為“/n”不是Y,執行了else的結果,所以顯示確認失敗。
? 解決方案:在 scanf 后加上一個“讀取 /n ”的 getchar()
int main(void) { char password[20] = {0}; printf("請輸入密碼:>"); scanf("%s", password); printf("請確認密碼(Y/N) :>"); // 清刷緩沖區; getchar() int ch = getchar(); if(ch == "Y") { printf("確認成功/n"); } else { printf("確認失敗/n"); } return 0; }
? (假設用戶輸入了123456;Y)確認成功
? (假設用戶輸入了123 456;Y)確認失敗
?“用戶輸入了空格,確認Y,為什么顯示確認失敗?”
? 解析:剛才加入的一個getchar()處理掉了空格,導致后面“/n”沒人管了;
? 解決方案:加入循環
int main(void) { char password[20] = {0}; printf("請輸入密碼:>"); scanf("%s", password); printf("請確認密碼(Y/N) :>"); // 清理緩沖區的多個字符; int tmp = 0; while( (tmp = getchar()) != "/n" ) { ; } int ch = getchar(); if(ch == "Y") { printf("確認成功/n"); } else { printf("確認失敗/n"); } return 0; }
? (假設用戶輸入了123 456;Y)確認成功
? 定義:
① 表達式1:初始化部分,用于初始化循環變量。
② 表達式2:條件判斷部分,用于判斷循環終止。
③ 表達式3:調整部分,用于循環條件的調整。
? 注意事項:
① 為了防止for循環失去控制,禁止在for循環體內修改循環變量。
② for循環內的表達式可以省略,但是得注意。
? 建議:
① 建議使用“左閉區間,右開區間”的寫法:
for( i=0; i<10; i++ ) 左閉,右開區間 ?for( i=0; i<=9; i++ ) 左右都是閉區間 ?
② 不要在for循環體內修改循環變量,防止for循環失去控制。
? for 的使用方法演示
① 利用 while 循環打印1~10數字:
int main(void) { int i = 1; // 初始化 while(i<=10) { //判斷部分 printf("%d ", i); i++; // 調整部分 } return 0;}
? 運行結果:1 2 3 4 5 6 7 8 9 10
② 利用 for 循環打印1~10數字:
int main(void) { int i = 0; for(i=1; i<=10; i++) { printf("%d ", i); } return 0;}
? 運行結果:1 2 3 4 5 6 7 8 9 10
? break 語句在 for 循環中的效果:
int main(void) { int i = 0; for(i=1; i<=10; i++) { if(i==5) { // 當i==5時; break; // 直接跳出循環; } printf("%d ", i); }}
? 運行結果:1 2 3 4
?? 什么沒有打印5?
? 解析:因為當 i==5 時,break 跳出了循環,循環中 break 之后的語句全都不再執行,printf 位于 break 之后,所以5自然不會被打印出來;
? continue 在 for 循環中的效果
if 中的 continue 會陷入死循環,但是在 for 中并不會:
int main(void) { int i = 0; for(i=1; i<=10; i++) { if(i == 5) continue; // 跳至調整部分(i++); printf("%d ", i); }}
? 運行結果:1 2 3 4 5 6 7 8 9 10
?? 這里為什么又沒打印 5?
? 解析:因為當 i==5 時,continue 跳至調整部分,此時 i++,i 為6。同上,所以5自然不會被打印。i 為6時,if 不成立,繼續打印,最終結果為 1 2 3 4 6 7 8 9 10(跳過了5的打印);
? for 循環體內修改循環變量的后果:
int main(void) { int i = 0; for (i=0; i<10; i++) { if (i = 5) { printf("haha/n"); } printf("hehe/n"); } return 0;}
? ? hehehahahehehaha…… ?死循環
? 定義:
① for 循環是允許嵌套的;
② 外部的 for 循環稱為外部循環,內部的 for 循環稱為內部循環;
? for 嵌套的演示:
int main(void) { int i = 0; int j = 0; for (i=0; i<10; i++) { for (j=0; j<10; j++) { printf("hehe/n"); } } // 10x10 == 100 return 0;}
? (打印了100個hehe)
? for 循環的省略:
① for 循環的 "初始化、判斷部分、調整部分" 都可以省略。
② 判斷部分的省略 - 判斷部分恒為真 - 死循環 ?。
③ 如果不是非常熟練,建議不要省略。
? 判斷部分的省略:
int main(void) { // 判斷部分恒為真 - 死循環 for(;;) { printf("hehe/n"); } return 0;}
? hehehehehehe…… ?死循環
? 省略帶來的弊端
假設我們希望下列代碼能打印 9 個呵呵:
int main(void) { int i = 0; int j = 0; for(; i<3; i++) { for(; j<3; j++) { printf("hehe/n"); } } return 0;}
?? 運行結果:hehe hehe hehe (只打印了3個)
? 解析:因為 i=0,內部 for 打印了3次 hehe,此時 j=3,這時 i++,j因為沒有初始化,所以此時 j仍然是3,而判斷部分要求 j<3,自然就不再打印了,程序結束。
? 請問要循環多少次?
int main(void) { int i = 0; int k = 0; int count = 0; for(i=0,k=0; k=0; i++,k++) { k++; count++; } printf("count:%d", count); return 0;}
? 答案:count = 0,一共循環0次。
? 解析:判斷部分 k=0,賦值為 0 時為假,所以一次都不會循環。
? 定義:在檢查 while() 條件是否為真之前,該循環首先會執行一次 do{} 之內的語句,然后在 while() 內檢查條件是否為真,如果條件為真,就會重復 do...while 這個循環,直至 while() 為假。
? 注意事項:
① do...while 循環的特點:循環體至少執行一次。
② do...while 的使用場景有限,所以不是經常使用。
③ 簡單地說就是:不管條件成立與否,先執行一次循環,再判斷條件是否正確。
? do...while 使用方法演示:
int main(void) { int i = 1; do { printf("%d ", i); i++; } while(i<=10); return 0;}
? 運行結果: 1 2 3 4 5 6 7 8 9 10
? break 語句在 do...while 循環中的效果:
int main(void) { int i = 1; do { if(i==5) { break; } printf("%d ", i); i++; } while(i<10); return 0;}
? 運行結果:1 2 3 4
? continue 語句在 do...while 循環中的效果:
int main(void) { int i = 1; do { if(i == 5) continue; printf("%d ", i); i++; } while(i<=10); return 0;}
? C語言中提供了可以隨意濫用的 goto 語句和標記跳轉的標號。最常見的用法就是終止程序在某些深度嵌套的結構的處理過程。
“ goto 語句存在著爭議”
1. goto 語句確實有害,應當盡量避免。
2. 理論上講goto語句是沒有必要的,實踐中沒有goto語句也可以很容易的寫出代碼。
3. 完全避免使用 goto 語句也并非是個明智的方法,有些地方使用 goto 語句,會使程序流程 更清楚、效率更高。
? 注意事項:goto 語句只能在一個函數內跳轉。
? 可以考慮使用 goto 的情形:
for(...) { for(...) { for(...) { // HOW TO ESCAPE? } }}
? 體會 goto 語句的特點:
int main(void) {flag: printf("hehe/n"); printf("haha/n"); goto flag; return 0;}
?? hehehahahehehaha (? 死循環)
? goto實戰:一個關機程序
C語言提供的用于執行系統命令的函數:system()
關機指令:shutdown?-s?-t?60 (60秒后關機)
取消關機:shutdown?-a
#include #include #include int main(void) { char input[20] = {0}; // 存放輸入的信息; system("shutdown -s -t 60"); // 關機指令; printf("[系統提示] 計算機將在一分鐘后關機 (取消指令:/cancel) /n"); again: printf("C://Users//Admin> "); scanf("%s", &input); if(strcmp(input, "/cancel") == 0) { system("shutdown -a"); // 取消關機; printf("[系統提示] 已取消。/n"); } else { printf(""%s" 不是內部或外部命令,未知指令。/n", input); printf("/n"); goto again; } return 0;}
Microsoft. MSDN(Microsoft Developer Network)[EB/OL]. []. .
百度百科[EB/OL]. []. https://baike.baidu.com/.
比特科技. C語言基礎[EB/OL]. 2021[2021.8.31]. .
本章完。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/121142.html
摘要:局部變量的作用域是變量所在的局部范圍。生命周期變量的生命周期變量的創建和銷毀之間的時間段局部變量的生命周期進入作用域生命周期開始,出作用域生命周期結束。 前言: 就在前幾天,C語言入門到進階部分的專欄——《維生素C語言》終于完成了。全文共計十八個章節并附帶三張筆試練習篇,美中不足的是,第...
摘要:語言中使用斜杠來表示一個字符串的結束。注意事項由于被替換,如果字符串末尾有,換行會出現兩次。函數的原型成功返回失敗返回將的字符串錄入到文件指針中。 前言: 考慮到之前在專欄中講字符串的時候有些知識點沒有詳細地講解,所以本篇是對字符串相關的知識點的補充篇!例如 %s 輸出左對齊右對齊,限制...
摘要:為此決定自研一個富文本編輯器。例如當要轉化的對象有環存在時子節點屬性賦值了父節點的引用,為了關于函數式編程的思考作者李英杰,美團金融前端團隊成員。只有正確使用作用域,才能使用優秀的設計模式,幫助你規避副作用。 JavaScript 專題之惰性函數 JavaScript 專題系列第十五篇,講解惰性函數 需求 我們現在需要寫一個 foo 函數,這個函數返回首次調用時的 Date 對象,注意...
閱讀 1388·2021-09-26 09:55
閱讀 1923·2019-08-30 12:45
閱讀 1065·2019-08-29 11:20
閱讀 3561·2019-08-26 11:33
閱讀 3428·2019-08-26 10:55
閱讀 1694·2019-08-23 17:54
閱讀 2391·2019-08-23 15:55
閱讀 2347·2019-08-23 14:23