# 期末考總整理 沒有編譯器?這好用 {%preview https://www.onlinegdb.com/ %} ## 複習/技巧 ### 1. ==左出右進== 這很重要 一堆人都會搞混,切記`cout <<`與`cin >>`! 然後要記得`std::`或`using namespace std;`。 ### 2.加減乘除不能省,電腦很笨(但知道四則運算) example: ```cpp= int a = 5, b = 6; cout << ab << endl; ``` ~~~ error(電腦不知道ab是什麼變數!) ~~~ 正解: ```cpp= int a = 5, b = 6; cout << a * b << endl; ``` ~~~ 30 ~~~ ### 3.清文沒教的實用東東:布林值 ~~是說那個林O浩的邏輯不太好,充要必要還不會(笑)~~ 跟`int`/`float`一樣是一種資料型態,但只有`true`跟`false`兩種可能,對應到數字就是非零為`true`零為`false`。再邏輯中條件回傳的就是布林。 example: ```cpp= int a = 0; if (a == 1) { // 回傳false cout << "case1" << endl; } else { cout << "case2" << endl; } ``` ~~~ case2 ~~~ 當然,也可以自己設 example: ```cpp= bool a = true; // 也可以寫bool a = 1; if (a == true) { //true,也可以簡寫為if(a)有同樣效果 cout << "case1" << endl; } else { cout << "case2" << endl; } ``` ~~~ case1 ~~~ ### 4. = 與 == 一個=是"指定",兩個=才是真正的"等於",你各位期中考多少人死在這自己自首!(笑 example: ```cpp= int a = 0; if (a = 1){ //1是true cout << "case1" << endl; } else { cout << "case2" << endl; } ``` ~~~ case1 ~~~ 因為a被指定成1了,非零者皆為真,所以才會變case1。 不過大於跟小於只有一個!! 兩個會變位元運算符(對,又一個清文沒說的東東) ps那如果是大於等於跟小於等於呢?答案是`>=` `<=`。怕搞混也可以用`||`弄成等於或小於(大於)的形式。 ### 5. `!` 的功能 `!`是做反轉功能,就是邏輯裡的"非",所以`!=`就是不等於,絕對跟階乘沒有關係,切勿排組做到走火入魔! example: ```cpp= int a = 5; if (a == 0) { cout << "case1" << endl; } if (a != 0) { cout << "case2" << endl; } ``` ~~~ case2 ~~~ ### 6.`return 0;`的意義 這是函式的概念,反正記得在main裡面用的話會中止整個程式。 當然,保險起見有的話是最好。 ### 7.一行程式的結尾`;` C++不是看換行斷句是看分號! 除了預處理命令(`#`開頭)都要加。 ## 期末考範圍:迴圈/陣列 ### 迴圈 那個叫林什麼浩的不會迴圈是不是~ (這我可以笑三年) ### 1.`for`:可以重複執行子區域內的程式碼 ```mermaid graph TD for-->初始式; 初始式-->判斷式; 判斷式-->False; False---->迴圈下之程式; 判斷式-->True; True-->陳述句; 陳述句-->遞增式; 遞增式-->判斷式; ``` 直接看範例: example: ```cpp= int a = 5; for (int i = 0; i < 5; i++) { a++; // 就是a += 1; } cout << a << endl; ``` ~~~ 10 ~~~ 重複五次加一。 ps: 在for控制敘述內(括號內)才宣告的迴圈變數(通常是i) **有效區域只有那個for裡面!!** 這個概念之後有緣再來聊,反正如果想要保留i的話必須在for之外宣告。 example: ```cpp= int a = 5; int i; for (i = 0; i < 5; i++) { a++; } cout << i << endl; ``` ~~~ 5 ~~~ 但如果這樣就錯,因為找不到i。 ```cpp= int a = 5; for (int i = 0; i < 5; i++) { a++; } cout << i << endl; ``` ~~~ error (電腦已經不認識i了) ~~~ ### 2.`while`:只要條件符合就一直重複 ```mermaid graph TD while --> 條件式 條件式 --> True 條件式 --> False True --> 重複執行之程式 重複執行之程式 --> 條件式 False ---> 迴圈下之程式 ``` 一樣直接看範例: example: ```cpp= int a = 5; while (a < 11) { a++; } cout << a << endl; ``` ~~~ 11 ~~~ 也是重複五次加一,但是否停止取決於a自己。 example: ```cpp= int a = 5; while ( a > 11) {//進來時a是5,不合條件 a++; } cout << a << endl; ``` ~~~ 5 ~~~ 這個while就完全沒有進去。 如果你想搞點事 example: ```cpp= int a = 5, bool b = true; while (b) {//true a++; } cout << a << endl; ``` ``` (對,沒有輸出,因為沒有結束的時候) ``` 可以直接寫: ```cpp= int a = 5; while (true) { a++; } cout << a << endl; ``` ### 3.`do-while`:先做再判斷 ```mermaid graph TD do-->重複執行之程式; 重複執行之程式-->條件式; 條件式-->True; 條件式-->False; True-->重複執行之程式; False-->迴圈下之程式; ``` 其實沒有很好用 example: ```cpp= int a = 5; do { a++; } while (a > 11); cout << a << endl; ``` ~~~ 6 ~~~ 理論上不該進這迴圈,但```do-while```強制讓他跑了一次 不過更建議複製貼上再執行while example: ```cpp= int a = 5; a++; while (a > 11) { a++; } cout << a << endl; ``` ~~~ 6 ~~~ ### 4.`break`跟`continue`:跳脫指令 有點玄,`break`是直接跳出迴圈,`continue`則是跳進下一輪迴圈。 請看範例 example: ```cpp= int a = 5; while ( a < 11) { a++; if (a == 8) { break; } } cout << a << endl; ``` ~~~ 8 ~~~ 到8就跳出來了。 ```cpp= int a = 5; while ( a < 11) { a++; if (a == 8) { continue; } cout << a << endl; } ``` ~~~ 6 7 9 10 11 ~~~ 到8時`cout`會被無視。 ==切記,只跳脫"迴圈",即`for`跟`while`,`if`不是!== ## 陣列 ### 1.陣列宣告 在宣告時用中括號表**長度(length)**,大括號表內容: example: ```cpp= int b[3]; int c[] = {1, 2, 3}; int d[5] = {1, 2, 3, 4, 5}; ``` 但切記,不可以既沒長度又沒內容(就像你各位的作文==) example: ```cpp= int a[];//這是違法的!! ``` 因為電腦不知道要申請多少記憶體空間。 ps:當然,陣列也未必要是整數陣列,也可以```float a[5];```, 或```bool b[]={true,true,false}```之類。 ### 2.陣列使用 在使用時,大括號內的數字是**索引值(index)**,20個人沒有第20號!! example: ```cpp= int c[] = {1, 2, 3}; cout << c[0] << " " << c[2] << endl; ``` ~~~ 1 3 ~~~ 所以以下是錯誤的 example: ```cpp= int c[] = {1, 2, 3}; cout << c[3] << endl; ``` ~~~ error (沒有3號!) // 會輸出奇怪數字 ~~~ ### 迴圈配陣列 這個應用必考!~~我感覺我好像對話式~~ 比如說輸出陣列內容或輸入,都可以用```for```搞定 example: ```cpp= int n = 5; int c[n]; for (int i = 0; i < n; i++) { c[i] = i; } for (int j = n - 1; j >= 0; j--) { cout << c[j] << " "; } ``` ~~~ 4 3 2 1 0 ~~~ ## 那些清文沒檢討的題目 供參考 ### 輸出三角形 example: 1 ```cpp= #include <iostream> using namespace std; int main() { for (int i = 1; i <= 5; i++) { for (int j = 0; j < i; j++) { cout << "*"; } cout << endl; } } ``` ~~~ * ** *** **** ***** ~~~ 2 ```cpp= #include <iostream> using namespace std; int main() { for (int i = 5; i > 0; i--) { for (int j = 0; j < i; j++) { cout << "*"; } cout << endl; } } ``` ~~~ ***** **** *** ** * ~~~ 3 ```cpp= #include <iostream> using namespace std; int main() { for (int i = 1; i <= 5; i++) { for (int j = 1; j < i; j++) { cout << " "; } for (int j = 0; j <= (5 - i); j++) { cout << "*"; } cout << endl; } } ``` ~~~ ***** **** *** ** * ~~~ 4 ```cpp= #include <iostream> using namespace std; int main() { for (int i = 1; i <= 9; i += 2) { for (int j = 0; j < (9 - i) / 2; j++) { cout << " "; } for (int j = 0; j < i; j++) { cout << "*"; } cout << endl; } } ``` ~~~ * *** ***** ******* ********* ~~~ ### 猜數字 example: ```cpp= #include <iostream> using namespace std; int main(){ int ans = 50;//任何數都可以 int counter = 0, input; while (true) { cout << "enter num:"; cin >> input; counter++; if (input < ans) { cout << "too small" << endl; } else if (input > ans) { cout << "too big" << endl; } else { break; } } cout<<"congratulation"<<endl<<"you tried "<<counter<< " times" << endl; return 0; } ``` ~~~ enter num:70 too big enter num:30 too big enter num:50 congratulation you tried 3 times ~~~ ## 稍微進階的概念 ~~(偷吃步)~~ ### algorithm裡的工具:sort 用來做排序,由小到大; 這我在期中考那份有用過,拿來找資料很方便,比如說那題找出最高分 期中考那份: {%preview https://hackmd.io/KDvSjVGrRbiWKpHEhOZlgQ %} 平凡人的寫法 example: ```cpp= #include <iostream> using namespace std; int main(){ int a[] = {3, 9, 2, 8, 1}; int max = 0; for (int i = 0; i < 5; i++) { if (max < a[i]) { max = a[i]; } } cout << max << endl; } ``` ~~~ 9 ~~~ 高手的寫法(經柏上身) example: ```cpp= #include <iostream> #include <algorithm> using namespace std; int main(){ int a[5] = {3, 9, 2, 8, 1}; sort(a, a + 5);//排序範圍內的元素 cout << a[4]; } ``` ~~~ 9 ~~~ 因為整個陣列被我換成了`{1,2,3,8,9}`,所以我只要抓最後一個就好。 可能有人會問為啥是加五?不是沒有`a[5]`這一項? 這是因為機制是範圍為頭到尾但不包含尾(左閉右開),我只能說 先背吧。 ### 隨機生成 可以讓電腦雖機丟數字給你,用剛剛那題猜數字來舉例 example: ```cpp= #include <iostream> #include <random> #include <cstdlib> using namespace std; int main() { srand (time (NULL));//先背...這不好解釋 int ans = (rand() % 100) + 1;//取亂數再限制範圍到1~100 int counter = 0, input; while (true) { cout << "enter num:"; cin >> input; counter++; if (input < ans) { cout << "too small" << endl; } else if (input > ans){ cout << "too big" << endl; } else { cout<<"error"<<endl; return 0; } } cout<<"congratulation"<<endl<<"you tried "<<counter<< " times" << endl; } ``` 其實這個亂數不是真正的亂數(偽隨機),但現在沒有很重要 ## 練習題 有空可以來玩玩 ### 1.(易)求總分平均 輸入五個整數,輸出總和與無條件捨去的平均值 ``` 10 20 30 40 50 ``` ``` 150 30 ``` ### 2.(中)找最大與次大 第一格輸入是陣列大小n,之後n格輸入是陣列的每一個元素,求最大者與次大者。 ``` 6 20 50 10 40 30 45 ``` ``` 50 45 ``` ### 3. (中)3N+1問題 輸入一整數,若為奇數則*3 + 1,偶數則 / 2,求出現的數形成之數列有幾項。 ``` 127 ``` ``` 47 ``` 到這裡都應該還算期末考可能考的難度,再往下應該就不會了 ### 4.(難)求孤單者 輸入9數(必然是一到五的整數),其中四個數出現兩次,輸出唯一只出現一次的數 ``` 3 1 4 5 3 1 4 2 2 ``` ``` 5 ``` ### 5.(更難)進階求孤單者 同上題,但輸入數之範圍擴大至非負整數。 ``` 6 20 9 8 9 71 20 8 6 ``` ``` 71 ``` ## 總結 期末考比起其中會更刺激更有趣,尤其是陣列配迴圈的操作一定考爛。電腦不會猜你意思,請務必搞清楚迴圈變數和陣列索引的關聯。 ==一定要練,一定要練,一定要練,看得懂不等於寫得出,多打才是真的學會。== 加油:) ![image](https://hackmd.io/_uploads/rkigl_Amgx.png)