1. ###### tags: `NSNote`
# 常用函式與應用二版
{%hackmd fssTA9u7QDCSoJc5aAGcUQ %}
## 1. **<cmath>**
a. pow(a,b); -> a 的 b 次方
b. sqrt(c);
c. cbrt(d);
d. hypot(e);
| pow(a,b) | sqrt(c) | cbrt(d) | hypot(e,f)
| -------- | -------- | -------- | ---------- |
| a 的 b 次方| 輸出 c 的根|輸出 c 的三次方根|輸出e^2 + f^2開根號 (對沒錯就是畢氏定理)|
**==-> 小實驗:能直接輸出浮點數嗎?==**
## **2. <cctype>**
### 1.字元測定函數
| isalpha(變數)| isalnum(變數) | isascii(變數) | isdigit(變數)|
| -------- | --------- | --------- | ---------|
| 若變數為英文字母,回傳1 | 若變數為英文字母或數字**字母**,回傳1 | 若變數屬於ASCII 0~127,回傳1 | 若變數為數字**字元**回傳1 |
**==->小實驗:isdigit()是判斷數字還是數字字元呢?==**
| isspace(變數) | islower(變數) | isupper(變數) |
|-----------|-----------|-----------|
| 若變數為空白字元,回傳1 | 若變數為小寫英文(a~z),回傳1| 若變數為大寫英文(A~Z),回傳1|
-> **[ascii](https://zh.wikipedia.org/wiki/ASCII)**
### 2. 字元轉換函數
|tolower(變數)|toupper(變數)|
|---------|---------|
|將字元A~Z轉換成 a~z |將字元 a~z 轉換成A~Z|
-> **==小實驗:若偵測到的字元不在更動範圍內的話,該字元會如何呢?==**
| toascii(變數)|
|-|
|用處不大,用強制轉型即可|
-> **發現 tolower 跟 toupper 轉換後會變 int,所以要顯示原本的英文字元,需使用強制轉型或putchar()**
```cpp=
cout << (char)tolower(a1) << "\n";
cout << (char)tolower(a2) << "\n";
cout << (char)toupper(a1) << "\n";
cout << (char)toupper(a2) << "\n";
```
### 補充:putchar()
```cpp=
putchar(tolower(a1));
putchar(tolower(a2));
putchar(toupper(a1));
putchar(toupper(a2));
```
會輸出:
aaAA
-> **所以putchar是直接輸出其字元,但沒辦法換行。**
## 3. **<algorithm>**
### 搜尋演算法
|find(front, end, value)|count(front , end, value)|
|-|-|
|從 front 到 end ( 不包含 end ) 找 value,若有就回傳第一個 value 的迭代器,若無則回傳 end|從 front 到 end ( 不包含 end ) 找 value 的數量,回傳 value 的個數|
search(front1, end1, front2, end2)|binary_search(front, end, value)|
|-|-|
|在front1到end1範圍中,找尋是否有依序出現front2到end2的每個元素,若有,回傳front2出現的迭代器,若無則回傳end1|二分搜尋,若value存在回傳true,否則回傳false(要先排序過)|
**以下兩函式須先排序**
|lower_bound(front, end, value)|upper_bound(front, end, value)|
|-|-|
|尋找第一個**不小於value**的迭代器,若不存在則回傳end|尋找第一個**大於value**的迭代器,若不存在則回傳end|
### 排序演算法
|sort(begin, end, cmp)|stable_sort(begin, end, cmp)|
|-|-|
|在begin到end範圍內排序,若無設定cmp比較函示,則使用預設的遞增排序。|同上,stable表示相同數值的元素,排序後相對位置不變。|
->何時適合用stable_sort?當你同時要排序不同的性質而希望順序不被打亂時。
### 集合演算法
此三種函式皆須先排序
|set_intersection(first1, last1, first2, last2, result)|set_union(first1, last1, first2, last2, result)|set_difference(first1, last1, first2, last2, result)|
|-|-|-|
|[first1, last1)範圍的資料與[first2, end2)的資料做**交集**,並把結果存在result中|[first1, last1)範圍的資料與[first2, end2)的資料做**聯集**,並把結果存在result中|[first1, last1)範圍的資料與[first2, end2)的資料做**差集**,並把對[first1, last1)的結果存在result中|
-> 以上三種都是以 [first1, last1) 優先儲存。
---
### 極值演算法
|min(a, b)|min_element(first, last)|
|-|-|
|回傳a與b中最小的,若相等則回傳a|在範圍內,找尋最小元素的迭代器,若有多個則回傳第一個|
|max(a, b)|max_element(first, last)|
|-|-|
|回傳a與b中最大的,若相等則回傳a|在範圍內,找尋最大元素的迭代器,若有多個則回傳第一個
->需注意max, min回傳的是值,而max_element, min_element回傳的則是位址。
### 排列演算法
須先排序
|next_permutation(first, last)|
|-|
|找尋下一個字母排序更大的結果|
```cpp=
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
int main(){
int arr[10] = {523,62,6,2462,542,5426,2,885,68,64};
sort(arr, arr + 10);
while(next_permutation(arr, arr + 10)){
for(int i = 0; i < 10; i++){
cout << arr[i] << " ";
}
cout << endl;
}
}
```
output:
各位可以自己嘗試,電腦壞掉別找我。
==以上是我能想到的,在打競賽程式會用到的一些function。當然還有很多實用的function,等你們慢慢探索==
## **HW:**
:::info
1.使用<cmath>,給直角三角形的兩個邊,求斜邊長。
:::
:::info
2.使用<cctype>,輸入一串英文句子,將第奇數個字改成大寫,第偶數個字改成小寫,**空白**及**標點符號**不包含在字的計數內。
e.g.:
input:I am a High scHOOl sTuDENt. GoOD.
output:I aM a HiGh ScHoOl StUdEnT. gOoD.
:::
:::info
3.第一行輸入a, b,代表兩組集合的數字數量。
第二行及第三行分別輸入a及b的內容,每組數字間會空格。
輸出分三行:
第一行輸出兩集合的交集。
第二行輸出兩集合的聯集。
第三行輸出兩集合的差集。
:::
:::info
4.輸入書本數 n,接下來每一行輸入一本書名及其價錢(之間空格)請先依價錢排序後,同價位再依書名字典序排序。最後輸出一行一本書,從最便宜的開始。(提示:用stable_sort)
**e.g. :**
**input :**
6
abc 150
acb 150
bac 200
bca 250
cab 200
cba 175
**output :**
abc 150
acb 150
cba 175
bac 200
cab 200
bca 250
:::