<style>
.reveal .slides {
font-size: 38px;
}
</style>
# 南大附中資訊研究社 NFIRC 1st
## 第 5 次社課講義
2023/12/06
主講:ShiYu
---
## 課前準備
- 開電腦 登DC ZJ...
- 南部資研社聯合寒訓參加意願調查

----
### 行政組工作人員招募

---
## 今日課程內容
- 迴圈複習
- 陣列 Array
- 迴圈與陣列的結合
- 字串
- 必做題
----
# 重要提醒
下次社課為「期末練習賽👨🏻💻」+「聚餐🍕」
這次社課學完記得要回去複習過一遍之前教過的所有內容
資源都幫大家彙整在這了 > [NFIRC 資源彙整](https://hackmd.io/@NFIRC/resource)
多多寫題單 期末賽的題目只要你有寫題單就會了
---
## 複習第 4 次社課內容
- 迴圈
- while 迴圈
- for 迴圈
- 迴圈控制
- continue
- break
----
## while 迴圈
當條件成立時 重複執行直到條件不成立
```txt=
while(條件成立時) {
重複執行這段程式碼
}
```
條件不成立時 電腦會退出迴圈並接著執行下面的程式
----
## 用 while 迴圈說 100 次 hello
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
int t = 100;
while(t--) {
cout << "hello\n";
}
return 0;
}
```
----
## 用 while 迴圈讀入 n 個數字並加總
輸入
```txt
5
10 40 20 80 50
```
程式碼
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
int n, a, sum = 0;
cin >> n;
while(n--) {
cin >> a;
sum += a;
}
cout << sum << "\n";
return 0;
}
```
----
## 重要技巧 EOF
輸入
```txt
10 40 20 80 50
```
程式碼
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
int n, sum = 0;
while(cin >> n) {
sum += n;
}
cout << sum << "\n";
return 0;
}
```
----
## for 迴圈
重複執行特定次數
```txt
for(初始值; 判斷式; 改變值) {
重複執行這段程式碼
}
```
----
## 用 for 迴圈輸出 1 ~ 10
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
for(int i = 1; i <= 10; i++) {
cout << i << " ";
}
return 0;
}
```
----
## 用 for 迴圈輸出 10 ~ 1
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
for(int i = 10; i > 0; i--) {
cout << i << " ";
}
return 0;
}
```
----
## 迴圈的控制
- continue
- break
----
## 請輸出 1 ~ 10, 但不要輸出 n
如果 n == 3 請輸出
```
1 2 4 5 6 7 8 9 10
```
如果 n == 8 請輸出
```
1 2 3 4 5 6 7 9 10
```
思考一下該怎麼做呢?
----
## continue 跳過此次 繼續執行下一次
請輸出 1 ~ 10 但不要輸出 n
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
int n;
cin >> n;
for(int i = 1; i <= 10; i++) {
if(i == n) {
continue;
}
cout << i << " ";
}
return 0;
}
```
----
## break 結束迴圈
---
## 陣列 Array
相同類型的元素所組成的資料結構
佔用連續區段的記憶體
----
如果我們要儲存三個數字
可以使用三個變數來存
```cpp=
int a,b,c;
cin >> a >> b >> c;
```
----
那如果我們要儲存 100 個數字呢?
用 100 個變數來存?
```cpp=
int a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z;
cin >> a >> b >> c >> d >> e >> f >> g >> h >> i >> j >> k >> l >> m >> n >> o >> p >> q >> r >> s >> t >> u >> v >> w >> x >> y >> z;
```
顯然英文字母都不夠用了 而且超麻煩
----
## 宣告陣列
與宣告變數的方法相同 只是多了 陣列大小
```cpp
int a; // 宣告變數
```
```cpp
int arr[5]; // 宣告陣列
```
示意圖

----
## 重要觀念
在 C++ 中 陣列 Array 的大小須事先宣告好
且為固定大小
若不知道要設多大
請仔細觀察題目給的數量範圍來決定
例如:有 $n$ 個數字 $1 \le n \le 1000$
就可以把陣列大小開到 arr[1000] 以上
----
## 如果不想一開始就宣告大小呢?
可以使用 C++ STL 內建資料結構中的 vector 動態陣列
下學期社課會教 STL 中各種實用的資料結構
這節課先把陣列的基礎打好就好
----
## 初始化
初始化變數
```cpp
int a = 10;
```
初始化陣列
```cpp
int arr[5] = {10,15,18,13,22};
```
初始化陣列(每項為 0)
```cpp
int arr[5] = {0};
```
----
## 索引值 index
元素在陣列中的位置
請記住 從 0 開始
----
## 陣列的讀取
```cpp=
#include <iostream>
using namespace std;
int main() {
int arr[5] = {10,15,18,13,22};
cout << arr[1] << "\n";
return 0;
}
```
輸出結果: ||<font>15</font> ||
----
### 注意:不要讀取超過陣列大小的索引值
```cpp=
#include <iostream>
using namespace std;
int main() {
int arr[5] = {10,15,18,13,22};
cout << arr[5] << "\n";
return 0;
}
```
會產生不預期的結果 請務必注意讀取範圍
----
## 陣列的修改
```cpp=
#include <iostream>
using namespace std;
int main() {
int arr[5] = {10,15,18,13,22};
a[1] = 20;
cout << arr[1] << "\n";
return 0;
}
```
輸出結果:||<font>20</font>||
---
## 迴圈與陣列的結合
學完什麼是陣列以及陣列的索引值
還有讀取與修改陣列元素的方法
接著回到一開始的問題
我們該如何儲存大量的資料呢
或許我們不該宣告一大堆變數然後手動輸入
我們可以使用前面學的迴圈搭配剛學的陣列
來輸入並儲存大量資料
----
變數的輸入
```cpp
int a;
cin >> a;
```
陣列的輸入
```cpp
int a[5];
for(int i = 0; i < 5; i++) {
cin >> a[i];
}
```
可以發現我們利用迴圈讓 i 遞增
剛好就可以運用索引值來修改陣列中的每個元素
----
變數的輸出
```cpp
cout << a;
```
陣列的輸出
```cpp
for(int i = 0; i < 5; i++) {
cout << a[i];
}
```
與輸入的概念相同 只是把迴圈中的 cin >> 變成 cout << 而已
----
## 陣列的排序
輸入
```txt
3 6 5 8 10 1 4 2 7 9
```
輸出
```txt
1 2 3 4 5 6 7 8 9 10
```
----
對於陣列中雜亂無序的整數
可以使用內建函式 sort()
來排序裡面的元素
使用方法:
sort(陣列名稱,陣列名稱 + 元素個數)
----
## 程式碼
```cpp=
#include <iostream>
using namespace std;
int main() {
int arr[10];
for(int i = 0; i < 10; i++) {
cin >> arr[i];
}
sort(arr, arr + 10);
for(int i = 0; i < 10; i++) {
cout << arr[i] << " ";
}
}
```
----
## 降序排序
sort()函式預設是由小排到大
如果要由大排到小 可以在函式中多加一個參數
```cpp=
// sort(陣列名稱, 陣列名稱 + 元素個數, 降序參數)
sort(arr, arr + 10, greater<int>());
```
----
## 排序演算法
初學者使用內建的排序函式就可以了
有興趣的人可以預習一下
[排序演算法 by ShiYu's Blog](https://4yu.dev/post/Sort-Algorithm/)
下學期有可能會教
---
## 字串 String
由 <font color="yellow">連續字元</font> 所組成 以 " " 包起來
----
## 什麼是字串
```cpp
"" // 空字串
"abcdef"
"ABCDEF"
"123456"
```
有用 " " 包起來的就是字串
----
## 如何宣告並初始化字串
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
string s0; // 宣告字串 預設為空字串
string s1 = "abcdef";
string s2 = "ABCDEF";
string s3 = "123456";
}
```
----
## 與陣列的相似之處
因為由連續的字元所組成
所以我們也可以用類似陣列的索引值
來存取字串中的單一字元
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
string s = "ABCDEF";
cout << s[0] << s[2] << "\n";
}
```
## 輸出結果: ||<font>AC</font>||
----
## 字串的串接
可以使用 + 將兩個字串相接起來
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
string s1 = "ABC";
string s2 = "123";
cout << s1 + s2 << "\n";
}
```
## 輸出結果: ||<font>ABC123</font>||
----
## 宣告空字串來玩文字接龍
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
string s;
char c;
while(cin >> c) {
s += c;
cout << s << "\n";
}
}
```
- 輸入:N F I R C 輸出:
```txt=
N
NF
NFI
NFIR
NFIRC
```
----
## 十進制轉二進制

----
## 使用字串串接來完成二進制轉換
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
int n;
string s;
cin >> n;
while(n != 0) {
if(n % 2 == 1) s = "1" + s;
else s = "0" + s;
n /= 2;
}
cout << s << "\n";
}
```
----
## 讀取一整行字串
如何讀取一整行字串而不是每次只讀進一個單字呢?
我們可以使用 getline 函數
語法:getline(cin,s)
----
## 使用 cin >> s

## 使用 getline(cin,s)

----
### 如何計算字串的長度
要計算字串的長度 我們可以使用 size() 函數
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main() {
string s;
while(getline(cin,s)) {
cout << s.size() << "\n";
}
}
```

---
## 延伸知識
- 各種字串的函數
- stringstream
- 競程技巧:建表
----
## 各種字串的函數
- empty():判斷字串是否為空
- resize():改變字串長度
- substr():產生子字串
- find():尋找子字串
- to_string():數字轉字串
- stoi():字串轉數字
課堂上不細講 有興趣了解使用方法請看[這篇](https://www.mropengate.com/2015/07/cc-string-stl.html)
----
## stringstream
用來處理特殊且複雜的輸入格式
[詳細使用方法文章](https://aprilyang.home.blog/2020/04/17/stringstream-to-read-int-from-a-string/)
----
## 競程技巧:建表
輸入:4 1 8 1 8 8
如何統計每個數字各出現幾次呢?
----

----
```cpp=
#include <bits/stdc++.h>
using namespace std;
int main()
{
int a[10] = {0};
int n;
while(cin >> n)
{
a[n]++;
}
for(int i=0;i<10;++i)
{
cout << a[i] << " ";
}
}
```

---
## 必做題
[c726,c717,a034,a022,a466]
這次題單只有 5 題 但 5 題都是必做題
因為下一次社課的練習賽有一題是這 5 題的綜合版
----
題解待更新
---
## 回饋表單
https://forms.gle/VLARSD79GCGLQU5z5

{"title":"第 5 次社課講義","slideOptions":"{\"parallaxBackgroundImage\":\"https://hackmd.io/_uploads/Syfv9UoH6.png\",\"backgroundTransition\":\"none\",\"transition\":\"slide\",\"transitionSpeed\":\"slow\",\"controlsBackArrows\":\"faded\",\"spotlight\":{\"enabled\":false}}","description":"2023/12/06主講:ShiYu","contributors":"[{\"id\":\"a5e01884-520b-4df5-8e23-bfcc32fb4697\",\"add\":8877,\"del\":1198},{\"id\":\"133c1d63-1697-43cd-a9d9-860f755172d1\",\"add\":107,\"del\":8}]"}