## 迴圈$(loop)$ ### 前言 如果我們現在要讓電腦輸出一萬個 "1" 是不是會一直ctrl+C ctrl+V 這種麻煩的工作交給電腦就對了 ouob 所以我們可以用到「迴圈」 ### $for$ 迴圈 > for(初始值;判斷式;更新值) > { >//statement > } :::success 如果$for$的敘述只有一行,可以不用加{ } ::: #### 順序 ```cpp= for(/*1*/初始值 ;/*2*/判斷式 ;/*4*/更新值) { /*3*/ //statement } ``` $1\rightarrow2\rightarrow3\rightarrow4\rightarrow2\rightarrow3\rightarrow4\ldots$ #### 初始值 直接定義一個變數,不一定要是$0$ >$int$ $long$ $long$ $float$ $double$ ... ```cpp= for(int i=0;判斷式;更新值) { //statement } ``` 或是使用原有的變數 ```cpp= float i; for(i=99;判斷式;更新值) { //statement } ``` #### 判斷式 < 大於 > 小於 == 等於 <= 大於等於 >= 小於等於 != 不等於 :::danger =是指定 ==才是等於 ::: 當判斷式正確時,就會執行敘述 ```cpp= for(int i=0;0<i<10;更新值) { //statement } /*----------*/ for(int j=100;j!=99;更新值) { //statement } ``` ```cpp= for(int i=0;i<(-1);更新值) { //statement } /*----------*/ for(int j=100;j<0;更新值) { //statement } ``` #### 更新值 讓迴圈有變化 也可以使迴圈停止 這個位置可以讓變數有變化 可以使用 + 加 - 減 * 乘 / 除 ... 下列是讓$i$加1的方法 > $i$=$i$+$1$ > $i$+=$1$ > $i$++ > ++$i$ ```cpp= int a=0,b=0; for(int i=10;i>0;i--) { a++; } for(int j=1;j<10;j*=2) { b++; } ``` :::spoiler 測驗 ```cpp= int i=0; for(i=1;i<5;i*=2) { } cout<<i<<endl; ``` 求輸出值。 --- 輸入$n$ 1+到$n$的總和。 :::spoiler 解答 ```cpp= #include<iostream> using namespace std; int main() { int n=0,sum=0; cin>>n; for(int i=1;i<=n;i++) sum+=i; cout<<sum<<endl; } ``` ```cpp= #include<iostream> using namespace std; int main() { int n=0,sum=0; cin>>n; sum=(1+n)*n/2; cout<<sum; } ``` ::: #### 無窮迴圈 當迴圈無論如何都達不到結束的條件 此時迴圈就不會結束 稱為無窮迴圈 e.g. ```cpp= for(int i=0;i<=999;i+=2) { i-=3; cout<<i<<endl; } ``` :::spoiler 測驗 ```cpp= int t=0; for(int i=1;i<=100;i++) { t+=1; i+=1; } cout<<t; ``` 求輸出值為多少? ($A$)100 ($B$)50 ($C$)0 ($D$)無輸出 --- ```cpp= int sum=0,n=50; for(int i=1;i<=n;i=sum) { sum+=i; } ``` 請問此$for$迴圈執行了幾遍? ($A$)7 ($B$)6 ($C$)5 ($D$)無窮迴圈 ::: --- ### $while$迴圈 while(判斷式) { } > 當判斷式成立時 > 執行一次敘述 > 依此循環 > 直到不符合判斷式 ```cpp= int i=0; while(i<100)//判斷式 { //statement i++;//重要!!! 這樣才會結束迴圈 } ``` :::spoiler while的其他用法 ```cpp= int n=0; while(cin>>n) { //statement } ``` 當輸入$n$時,執行敘述 直到輸入^$Z$(ctrl+Z),迴圈才會結束 適用於需要輸入多筆資料的時候 --- ```cpp= while(n--) { } ``` 每次碰到都會執行一次括號內的敘述 讓迴圈內的敘述執行$n$遍 等同於 ```cpp= for(n=n;n>0;n--) { } ``` --- ```cpp= while(ture) { //statement } while(1) { //statement } ``` ##### 判斷式 (100==100)$\rightarrow true$ (1==0)$\rightarrow false$ 當判斷式內是$true$時,迴圈就會一直執行,變成無窮迴圈 ::: #### 測驗 > [ZeroJugde a005](https://zerojudge.tw/ShowProblem?problemid=a005) :::spoiler code ```cpp= #include<iostream> using namespace std; int main() { int t=0; cin>>t; while(t--) { int a=0,b=0,c=0,d=0; cin>>a>>b>>c>>d; cout<<a<<' '<<b<<' '<<c<<' '<<d<<' '; if(b-a==c-b) cout<<d+(b-a)<<endl; else cout<<d*(b/a)<<endl; } return 0; } ``` ::: > [ZeroJugde a244](https://zerojudge.tw/ShowProblem?problemid=a244) :::spoiler code ```cpp= #include<iostream> using namespace std; int main() { int n=0; cin>>n; while(n--) { long long a=0,b=0,c=0; cin>>a>>b>>c; if(a==1) cout<<b+c<<endl; else if(a==2) cout<<b-c<<endl; else if(a==3) cout<<b*c<<endl; else cout<<b/c<<endl; //整數輸出 } return 0; } ``` ::: ### 特殊 > 跳出目前的迴圈 ```cpp= break; ``` :::spoiler 範例 ```cpp= #include<iostream> using namespace std; int main() { int a=0,b=0; for(int i=0;i<100;i++) { a++; if(i==10) break; b++; } cout<<a<<' '<<b<<endl; } ``` ::: > 進行下一次的循環 ```cpp= continue; ``` :::spoiler 範例 ```cpp= #include<iostream> using namespace std; int main() { int a=0,b=0 for(int i=0;i<10;i++) { a++; if(i%2==1) continue; b++; } cout<<a<<' '<<b<<endl; } ``` ::: :::info 兩者通常搭配 $if$ 使用 ::: --- ## 陣列 $(array)$ 一個數列 4,7,5,45,11,... ![](https://hackmd.io/_uploads/Sk6ISYltn.png) ### 宣告 ```cpp= int a[5]; int b[5]={0,1,2,3,4}; int c[ ]={0,1,2,3,4}; int d[5]={0,1,2}; float e[5]={}; double f[5]{}; long long g[5]={0}; ``` ### 呼叫 ```cpp= int num=a[0]; for(int i=0;i<n;i++) { cout<<a[i]<<" "; } ``` ### 輸入 ```cpp= int a[n]; for(int i=0;i<n;i++) { cin>>a[i]; } ``` ### 加總 ```cpp= int sum=0; for(int i=0;i<n;i++) { sum+=a[i]; } ``` #### 測驗 給定一個陣列{1,2,3,4,5} 請將他反過來輸出。 :::spoiler code ```cpp= #include<iostream> using namespace std; int main() { a[5]={1,2,3,4,5}; for(int i=4;i>=0;i--) { cout<<a[i]<<' '; } return 0; } ``` ::: --- 輸入$n$,$x$和一個長度為$n$的陣列 試找出$x$的位置。 :::spoiler code ```cpp= #include<iostream> using namespace std; int main() { int n=0,x=0; cin>>n>>x; int a[n]; for(int i=0;i<n;i++) cin>>a[i]; for(int i=0;i<n;i++) { if(x==a[i]) { cout<<i<<endl; break; } } return 0; } ``` ::: --- 輸入$n$和一個長度為$n$的陣列 求偶數項的和。 :::spoiler code ```cpp= #include<iostream> using namespace std; int main() { int n=0,sum=0; cin>>n; int a[n]; for(int i=0;i<n;i++) cin>>a[i]; for(int i=0;i<n;i++) { if(i%2==1) { sum+=a[i]; } } cout<<sum; return 0; } ``` ::: --- 輸入$n$和一個長度為$n$的陣列 求陣列的平均。 :::spoiler code ```cpp= #include<iostream> using namespace std; int main() { int n=0,sum=0; cin>>n; int a[n]; for(int i=0;i<n;i++) cin>>a[i]; for(int i=0;i<n;i++) sum+=a[i]; cout<<sum/n<<endl; } ``` ::: --- ### 界外 當在呼叫陣列時,超出了陣列的範圍 這時就有可能會出錯。 ```cpp= int a[5]={1,2,3,4,5}; int num=a[5]; ``` ## 補充 ### $do$ $while$迴圈 後判式 > do > { >//statement >}while(判斷式) 會先執行敘述,再進行判斷式 ```cpp= int i=0,a=0 do { a++; }while(i<5) ``` ```cpp= int j=0,b=0 do { b++; }while(j>=b) ``` --- ### $char$陣列 ![](https://hackmd.io/_uploads/SJGnFfZF3.png) 最後一格會是"\0",作為結束的標記 所以$char$陣列會比初始設定的大小少一格 ```cpp= char a[6]; for(int i=0;i<5;i++) cin>>a[i]; for(int i=0;i<5;i++) cout<<a[i]; ``` 字元陣列可以使用陣列名稱輸入輸出,可以不用迴圈 ```cpp= char b[6]; cin>>b; cout>>b; ``` ::: info input: Hello output: Hello ::: > [name=wi11y][time=July 2, 2023][color=#E0FFFF]