# C語言筆記 ## 2022/8/3 ```c= #include <stdio.h> #include <stdlib.h> int main() { printf("Hello world!\n"); return 0; } ``` **{}**:一個大括號表示一個區塊的開始與結束 **printf("要輸出的文字")** **\n** **跳脫字元** =>用來換行:每輸出一個\n就會換行一次 **用()包起來的是字串** =>要跟程式碼中的其他指令做區別 **用""包起來的是字元** <font color="#f00">*printf為一段已經寫好的程式碼,若憑空使用它,編譯器無法辨識,則須於開頭使用<font color="#00f">#include</font>,使編譯器去找到<font color="#00f">stdio.h</font>這個檔案</font> <font color="#00f">stdio.h</font> 為c語言內建的檔案,裡面有關於**printf**這個函數的用法;<font color="#00f">include</font>則會把這個檔案的內容加進程式碼 **return**:回傳一個結果=>return 0:回傳0這個值,表示程式成功執行完畢 **;分號**:C語言中的結束語句,表示當前語句已終止,其後的其他語句是新語句 <font color="#f00">***常見的跳脫字元:***</font>\n:用來換行         \t:用來縮排(<font color="#00f">等同於輸出一個 tab</font>)         \’:用來輸出一個單引號         \”:用來輸出一個雙引號         \\\:用來輸出一個反斜線 ### 練習 文字圖形 ![](https://i.imgur.com/v2ZecX6.png) **寫法一** ![](https://i.imgur.com/YPzRibQ.png) **寫法二** ![](https://i.imgur.com/tKtauwl.png) <font color="#f00">*</font>**寫法三** ![](https://i.imgur.com/vRB4fii.png) ## 2022/8/5 ```c= #include <stdio.h> #include <stdlib.h> int main() { int integer1; int integer2; int sum; printf("Please enter the first integer "); scanf("%d", &integer1); printf("Please enter the second integer "); scanf("%d", &integer2); sum=integer1+integer2; printf("sum is %d.\n",sum); return 0; } ``` **int 變數**:一個整數的變數,於此程式碼為一個名稱叫integer1(integer2/sum)的整數(名稱可自取) **scanf**:表示從鍵盤讀入資料 **%d**:表是一個十進位的整數 **&取址運算子**:取址,取得位址,於此程式碼中取得名稱叫integer1(integer2/sum)的位址 **scanf函式:<font color="#f00">scanf("%d", &integer1)</font>**      從鍵盤讀入一個十進位的整數, 將它儲存在變數integer1裡面 **=指定運算子**:將右邊的結果算出來後,存入左邊的變數裡面 **printf("sum is %d.\n",sum)**: 此段程式碼運用類似跳脫的概念![](https://i.imgur.com/d8KZHAl.png) **%d**類似一個替代品,替代逗號後的參數**sum** ### 練習 三個數字的和 ![](https://i.imgur.com/NFHzHrh.png) **寫法一** ![](https://i.imgur.com/5weHkc1.png) **寫法二** ![](https://i.imgur.com/16Ds6Bt.png) ## 2022/8/8 ### 數值交換 ![](https://i.imgur.com/pAt45I2.png) **我的寫法** ```c= #include <stdio.h> #include <stdlib.h> int main() { int integer1, integer2,integer3; printf("Please enter the first integer "); scanf("%d", &integer1); printf("Please enter the second integer "); scanf("%d", &integer2); integer3=integer1; integer1=integer2; integer2=integer3; printf("integer1: %d.\n",integer1); printf("integer2: %d.\n",integer2); return 0; } ``` ![](https://i.imgur.com/Xf4hjz6.png) **其他寫法** ```c= #include <stdio.h> #include <stdlib.h> int main() { int integer1, integer2; printf("Please enter the first integer "); scanf("%d", &integer1); printf("Please enter the second integer "); scanf("%d", &integer2); integer1=integer1+integer2; integer2=integer1-integer2; integer1=integer1-integer2; printf("integer1: %d.\n",integer1); printf("integer2: %d.\n",integer2); return 0; } ``` ==integer1=integer1+integer2;== ==integer2=integer1-integer2;== ==integer1=integer1-integer2;== <font color="#f00">此寫法使用限制:變數須為可加減之變數</font> ### 資料型別 ( Data type ) 資料的型別會決定一個資料要怎麼儲存和計算 ### 資料的儲存 * 電腦的記憶儲存空間是以位元組 ( byte ) 為單位組成 <font color="#f00"> | byte | byte | byte | ...... | byte | | ---- | ---- | ---- | ---- | ---- | </font> * 每個位元組 ( byte ) 由多個位元組成 ( bit ) * 一個位元組一般由8個位元構成 ( 實際個數為實作定義 ) * 每個位元 ( bit ) 可表示0或1種值 * 任何資料型別的資料都可以轉匯成一串由0跟1組成的的序列來表示 ### C語言常見的內建資料型別 | 資料型別 | 名稱 | 大小 ( 位元組 ) | 例子 | |:------------------------------------------------:|:---------:|:---------------:|:----:| | 短整數(short integer) | short int | 2* | 32 | | 整數(inteter) | int | 4* | 32 | | 長整數 ( long integer ) | long int | 4* | 32 | | 字元 ( character ) | char | 1 | ‵3′ | | 單精福點數度 ( single-precision fioating point ) | float | 4* | 3.2 | | 倍精福點數度 ( double-precision fioating point ) | double | 8* | 3.2 | | 無名稱 | void | ? | | **==<font color="#f00">*</font>表示該大小為實作定義==** ### 使用 sizeof 看所占記憶空間的大小 * 許多型別占用的記憶體空間大小皆由「實作定義」決定,隨使用的編譯器或設定不同而可能有異 * eg:long int大小不一定為4 ( byte ) ;在某些64bit的編譯器中,long int大小不一定為8 ( byte ) 或其他大小 * sizeof運算子可以去求使用的編譯器的某個值或型別所佔的記憶體大小 ( 單位為byte ) 使用方式:**printf("long int: %d.\n",sizeof(long int))** ### 定義變數 * 變數名稱使用前,需先宣告或定義 * 變數定義時需要指定名稱與型別: * <font color="#00f">資料型別</font> <font color="#0f0">變數名稱</font>; * <font color="#00f">int</font> <font color="#0f0">num</font>; ==(讀取未指定值的變數在大部分情形下是「未定義行為」)== * 在定義時也可以直接指定初始值,稱為初始化 * <font color="#00f">int</font> <font color="#0f0">num</font> = 0; #### 命名限制 * 名稱須由英文大小寫字母、數字與底線組成 * 數字不能開頭 * 字母大小寫不同則代表不同的名稱 * **以下字詞不可作為命名名稱使用** auto, break, case, char, const, continue, default, do, double, else, enum, extern, float, for, goto, if, int, long, register, return, short, signed, sizeof, static, struct, switch, typedef, union, unsigned, void, volatile, while ### 不同資料型別間的差異 * 表示的資料意涵不同:**整數**(int)與**字元**(char) * 表示的原理不同:**整數**(int)與**浮點數**(float) * 可表示的值範圍不同:**短整數**(short int)與**長整數**(long int) * 可表示的精確度不同:**單精度浮整數**(float)與**倍精度浮整數**(double) * 有無正負數(有號與無號)的不同:**有號整數**(int)與**無號整數**(unsigned int) ## 2022/8/16 ### 浮點數型別 * 浮點數(floating point)是可用來表示實數的一種方法 * 浮點數可表示帶小數的數值 * 浮點數所表示的可能只是一個約略值 * 在佔用一樣大記憶體空間的情況下,浮點數可表示的範圍可以大於整數表示法 * 一樣占用4個位元組,整數二進位表示法的範圍約為10位數,但浮點數可以到將近40位數 * 浮點數可以想成是一種科學記號表示法 ### 有效數字 * 圓周率:3.14159265..... * 取三位有效數字:3.14 * 取四位有效數字:3.141或3.142 * 有效數字位數越多,值越精確,需要記憶的資訊也越多(**需占用更多記憶體空間**) * 使用整數表示法儲存的整數,只要在可表示的範圍內都屬於有效數字(無誤差) ### 科學記號表示法 123.45 →1.2345 x 10² →<mark>1.23</mark>  x 10<font color="#00f">²</font>  →  123  2 取三位有效數字     (有效數字) (指數) <font color="#f00">此為將儲存一個實數的問題變成兩個實數的問題</font> 12345000000    ←<font color="#00f">用4個位元儲存的整數無法表示這個數字(溢位)</font> →1.2345 x 10¹⁰ →<mark>1.23</mark>  x 10<font color="#00f">¹⁰</font>  →  123  10 取三位有效數字     (有效數字) (指數) 0.0078901     →7.89 x 10⁻³ →<mark>7.89</mark> x 10<font color="#00f">⁻³</font>  →    789     -3 取三位有效數字     (有效數字) (指數) ### C語言常見的內建浮點數型別 | 資料型別 | 名稱 | 大小(位元組) | 有效數字大小(位元) | 指數大小(位元) | |:------------------------------------------------:|:-----------:|:------------:|:------------------:|:--------------:| | 單精福點數度 ( single-precision fioating point ) | float | 4* | 23*(約6位位數) | 8* | | 倍精福點數度 ( double-precision fioating point ) | double | 8* | 52*(約15位數) | 11* | | | long double | 8* | ?* | ?* | * 浮點數依然可能會溢位→造成未定義行為 <font color="#f00">其中一個位元通常用來表示正負數</font> <font color="#00f">* 表示大小為實作定義</font> ### 浮點數使用的優缺點 * 優點 * 相較占用同大小的整數格式,浮點數可以表示的數值範圍較廣,比較不容易溢位 * 可以自然的表現小數 * 缺點 * 浮點數表示的可能只是約略值,在做精確計算或比較時可能發生不預期的結果 * 格式較整數格式複雜,做運算時可能效率較差 * 現代電腦內部通常會有專門為浮點數運算設計的硬體 ## 2022/08/23 ### printf 的使用 * printf是做標準輸出的一個內建函式 * 通常'<font color="#00f">標準輸出</font>'意思就是把輸出的文字印到螢幕上 * printf使用時要給予想要輸出的字串 → printf("<font color="#f00">要輸出的字串</font>"); eg: printf("<font color="#f00">hello!</font>"); ### printf 的格式字串 * printf輸出的字串可以用類似字元跳脫的方法,放置一些<font color="#f00">格式符</font>來輸出特定格式的資料 eg:  int sum=<font color="#f00">10</font>;     printf(<font color="#00f">"sum is %d"</font>,sum);      →printf(<font color="#00f">"sum is %d"</font>,<font color="#f00">10</font>);      →printf(<font color="#00f">"sum is 10"</font>); ### 用printf 輸出整數時常見的格式符 * 在格式字串中,以%為跳脫記號,後面可加下表中的格式符代表要輸出的格式 | 格式符 | 輸出格式 | 以輸出十進位的123為例 | |:------:|:----------------------:|:---------------------:| | d或i | 十進位有號整數 | 123 | | u | 十進位無號整數 | 123 | | o | 八進位無號整數 | 173 | | x | 十六進位無號整數(小寫) | 7b | | X | 十六進位無號整數(小寫) | 7B | ## 2022/08/26 ### 用printf輸出不同格式的整數 ```c= int a =123456789; unsigned int b =3000000000; printf("%d\n",a); //123456789 →(o) printf("%d\n",b); //-1294961296 →(x) printf("%u\n",b); //3000000000 →(o) ``` <mark>理由:%d 為有號整數格式,無號整數格式應為%u</mark> ### 用printf輸出浮點數時常見的格式符 | 格式符 | 輸出格式 | 範例 | |:------:|:--------------------------------:|:------------:| | %f | 十進位浮點數 | 123.45 | | %e | 科學記號表示法(小寫) | 1.234500e+02 | | %E | 科學記號表示法(大寫)1.234500E+02 | 1.234500E+02 | ### scanf的使用 scanf為一個做標準輸入的內建函式 格式scanf(<font color="#00f">"要讀入的資料格式"</font>,<font color="#00f">變數位址</font>);   →scanf(<font color="#00f">"%d"</font>,<font color="#00f">&a</font>); ### 用scanf輸出浮點數時常見的格式符 | 格式符 | 輸出格式 | 範例 | |:------:|:--------------:|:------:| | %i | 任何格式的整數 | 123 | | %d | 十進位有號整數 | 123 | | %u | 十進位無號整數 | 123 | | %f | 十進位浮點數 | 123.45 | ### 計算平均 如何將三個十進位數值計算至小數位 ```c= #include <stdio.h> #include <stdlib.h> int main() { int a,b,c; printf("輸入數字一:"); scanf("%d",&a); printf("輸入數字二:"); scanf("%d",&b); printf("輸入數字三:"); scanf("%d",&c); double average = (a+b+c) / 3.; //將int改成double //將3後面加上. printf("average:%f",average); //將%d改成%f return 0; } ``` #### 整數或浮點數做算術運算的結果 當兩個同為整數浮點數的值做算術運算時,其結果為同樣的型別 eg:(int)+(int)→(int)   (float)+(float)→(float) #### 思考 <font color="#00f">double average = (a+b+c) <mark>/ 3</mark>;</font>→/3未被定義型別,預設為十進位整數(int),為**字面常數** →<font color="#00f">(a+b+c)/ 3</font>→ (int)/(int)得到(int) → 做整數除法並捨取餘數 **常見字面常數** | 常見字面常數 | 型別 | |:------------:|:------------:| | 123 | int,long int | | 123.45 | double | | 123.45f | float | **double  average =   3 ;** →轉型→ **double  average =  3.0000  ;**      (double)   (int)           (double)  (double) 此稱為<font color="#f00">隱性轉型</font>:當整數轉型成浮點數時,如果在可表示的範圍裡,會轉型成最接近的浮點數值 <font color="#00f">double average = (a+b+c)   <mark>/ 3. </mark> ;</font> → <font color="#f00">/3.</font>為浮點數型別(double)          (int)   (double) ***當兩個不一樣整數或浮點數型別的值做算術運算時,如果可以算,會隱性轉型成範圍較大的型別並算出該型別的值** #### 隱性轉型與顯性轉型 * 隱性轉型 double average = (a+b+c) /<font color="#f00"> 3.</font>; * 顯性轉型 double average = (a+b+c) / <font color="#f00">(double) 3  </font>;                  (int) ### 字元型別 * C語言主要有兩種字元型別 * **char** * **wchar_t** * 一般我們使用的是char型別,wchar_t型別使用在**寬字元** * char型別占用的記憶體大小為一個位元組 * 中文字有幾種可能? * 使用<font color="#00f">多個char</font>或<font color="#00f">wchar_t</font>表示 #### char型別 * 特色 * 常見的是使用ASCII編碼 * 型別占用一個位元組 * 是一種**整數**的型別 * 字面常數 * 用一組單引號括住:<font color="#f00">'A' 'a' '0' '\n'</font> <mark><font color="#f00">*</font>用雙引號""括住的是字串</mark> * printf與scanf的字元格式符:**%c** #### 使用char ```c= #include <stdio.h> #include <stdlib.h> int main() { char ch = 'A'; //宣告定義一個叫做ch的字元變數,並初始化為'A' printf("%c\n",ch); //用字元的格式印出ch字元變數的內容 return 0; } ``` ```c= #include <stdio.h> #include <stdlib.h> int main() { char ch = 'A' + 1; //→變為B printf("%c\n",ch); return 0; } ``` #### char 型別的算數運算 * 'A' + 1 得 'B' * 'a' + 1 得 'b' * 'A' - 1 得 '@' * 'A' + '1' 得 'r' 如何得知?→ <font color="#f00">ASCII碼對照表</font> ![](https://i.imgur.com/gLJ0NNN.png) ### 練習 字元大小寫的轉換 寫一程式,讓使用者輸入一個大寫字母後,將其轉換成對應的小寫英文字母後輸出 **寫法一** ```c= #include <stdio.h> #include <stdlib.h> int main() { char A; printf("請輸入一個大寫字母: "); scanf("%c",&A); char a = A+32; printf("%C",a); return 0; } ``` ![](https://i.imgur.com/lIknPJf.png) **寫法二** ```c= #include <stdio.h> #include <stdlib.h> int main() { char A; printf("請輸入一個大寫字母: "); scanf("%c",&A); char a = A+('a'-'A'); printf("%C",a); return 0; } ``` ## 2022/09/11 ### 型別選擇 | 用途 | 型別 | 注意 | printf 格式符 | scanf 格式符 | |:--------------------------:|:------:|:------------------:|:-------------:|:------------:| | 整數(一般情況) | int | 不要算到超過九位數 | %d | %d | | 浮點數(帶小數or為數過多) | double | 可能與真實質有差 | %f | %lf | | 字元(可讀文字) | char | | %c | %c | ### 運算元、運算子、表示式 <mark>3<font color="#f00">+</font>5<font color="#f00">*</font>2</mark> → 此為表示式,紅色部分為運算子,其餘部分為運算元 **運算元**:資料,具有型別跟值   **運算子**:對資料做運算    **表示式**:表示一筆資料,具有型別跟值 <font color="#f00">*</font>運算子間有先後順序,一次執行一個運算,遵循一般的數學概念 ![](https://i.imgur.com/jFbObCo.png) ![](https://i.imgur.com/aGuxCrk.png) ![](https://i.imgur.com/FWFZAeX.png) ![](https://i.imgur.com/qzRDpKP.png) ![](https://i.imgur.com/IADAmN3.png) ![](https://i.imgur.com/9k31qYV.png) ![](https://i.imgur.com/JVec8lI.png)