# C# 社課 ###### tags: `興附電研21th` `C#` > 目標:學習 C# 的基礎語法 --- - 本單元索引 [ToC] --- # 第一週 :one: ## 1.學 C# 的常見問題 ? ### Q. C# 的用途有哪些 - [x] 控制台 - [x] 桌面程式:Winform, WPF, UWP :desktop_computer: - [x] 網站:ASP.NET - [x] 2D/3D 遊戲:Unity :video_game: - [x] 手機APP、機器學習...... :mag_right: ### Q. APCS 的測驗內容沒有C#,這樣之後會不會很吃虧 ? A. 其實完全不用害怕呦~ 就我所知,==C++、C#、JAVA、C== 這四種程式語言的語法、編寫風格都很相近的哦 ! 只要精通其中一種程式語言,想再學習其他語言都不是問題~ :::info :bulb: APCS可以使用的程式語言有 C、C++、Python、Java ::: > 如果想參加考試檢定的可以參考下圖呦! ( Reference:吳邦一教授 ) > ![](https://i.imgur.com/4nQTEL9.png) ## 2.Visual Studio Code ( 簡稱vscode ) 設定 ### Step 1: 在桌面上創一個新的資料夾 ( 中英文隨意 ) ![](https://i.imgur.com/wP7mAUh.png) --- ### Step 2: 打開桌面上的 Visual Studio Code ![](https://i.imgur.com/pmUfqdU.png) #### 打開後會有下面這個樣子的視窗 ![](https://i.imgur.com/IVetLLN.png) #### 再來將鼠標移至上方選單的檔案,拉開之後再點選開啟新的資料夾 ![](https://i.imgur.com/i85y5v6.png) #### 接著選擇剛剛創建的資料夾就成功瞜~ --- ### Step 3: 安裝 C# 延伸模組 #### 將鼠標移至左方選單,並點有四個格子的那個圖案 ![](https://i.imgur.com/owEozjP.png) #### 點開他後,搜尋欄打==C#==,並安裝 C#、C# Extensions ![](https://i.imgur.com/lcpb0Dy.png) ![](https://i.imgur.com/bE2Gl5q.png) #### 安裝完後鼠標移到上方選單的終端機,選擇新增終端,接著在終端機打上"dotnet new console",打完按enter ![](https://i.imgur.com/RoJ78FR.png) #### 接著鼠標移至左方選單的檔案總管,點下去就可以看到程式碼啦~ >如果沒有看見就點一下左邊列表的 Program.cs > ![](https://i.imgur.com/mNvrbyU.png) ![](https://i.imgur.com/r09Sm4J.png) >如果還是空的話,就複製下方的程式碼貼上去吧~ ```csharp= using System; namespace HelloWorld { class Program { static void Main(string[] args) { Console.WriteLine("Hello World!"); } } } ``` --- ### Step 4: 執行第一支程式吧! #### 在終端機裡面打 "dotnet run",接著等一下就可以看到東西印出來了哦~ ![](https://i.imgur.com/brhbpvK.png) >可以拍現動炫耀了ㄎㄎ ( X :::info :bulb: 記得在檔案那邊勾選自動儲存,不然就算更改了還是會輸出Hello World! ::: --- ### 再來就開始學基本的輸入輸出還有變數吧~ #### 1. 常見的變數類別 https://ithelp.ithome.com.tw/articles/10213219 #### 2. 基本輸入輸出 https://ithelp.ithome.com.tw/articles/10213373 --- # 第二週 :two: ## 1.程式是怎麼運行的 ### **程式執行的簡要概念** * #### 程式被激活 ---> 從硬碟中讀取==資料 (data)==、==指示 (instructions)== * #### 程式中的指示會==依照順序被cpu執行== * #### CPU具有==運算邏輯單元 (ALUS)== :::info :bulb: 以人體的部位來比喻的話,CPU就像是大腦 ::: --- ### **記憶體階層 (Memory Hierarchy)** ![](https://i.imgur.com/Tc2wREa.jpg) * #### L2以上都在CPU內 -- 暫存器、快取記憶體 (靜態隨機存取記憶體 SRAM) * #### Main memory -- 動態隨機存取記憶體 (DRAM) * #### Local secondary storage -- 傳統硬碟 (HDD)、固態硬碟 (SSD) * #### Remote secondary storage -- 雲端硬碟 --- ### **C# 結構 (Structure)** ```csharp= using System; //使用 System 命名空間 namespace HelloWorld //namespace 稱為 命名空間 { class Program //有一個 class 叫作 Program { // 這個 class 裡面有一個 Main 方法 (method) static void Main(string[] args) { //使用 System (命名空間) 中的 Console (類別) 的 WriteLine (方法) Console.WriteLine("Hello World!"); // 執行結果 HelloWorld! } } } ``` * #### using System -- 表示讓程式包含 System (命名空間) * #### 在 HelloWorld (命名空間) 中,有一個 Program (類別),此類別中只有一個 Main (方法) * #### Main() 方法在 C# 中表示==程式的進入點== * #### // (雙斜線) 在 C# 中的功能是註解,程式執行的時候會自動忽略過去 * #### Console.WriteLine("HelloWorld!") > ##### 使用定義於 System (命名空間) 中的 Console (類別),而 WriteLine (方法) 定義於 Console (類別) * #### C# 文件的後綴詞是 .cs * #### 一些符號的功能 | 符號 | 功能 | |:-------:|:-------------------------:| | **( )** | **通常用於方法 (method)** | | **{ }** | **劃定範圍** | | **[ ]** | **用於陣列 (Array)** | | **//** | **註解** | | **;** | **表示語句的結束** | | **" "** | **字串** | --- ### **程式的運行錯誤 (Bug)** #### 當運行程式的時候,發現答案跟預期的結果不同,大致可分為三種問題 #### 1. CE (Compile Error) -- 表示程式在編譯的時候發生錯誤,通常為語法問題 #### 2. RE (Runtime Error) -- 表示程式在執行的過程中發生錯誤,常見的狀況像是超出陣列大小 #### 3. LE (Logic Error) -- 表示使用者個人的邏輯問題,此問題最難解決 --- ### **縮排 (Programming Style)** #### ==好的縮排可以讓其他人在讓程式更容易閱讀== ##### 1. 沒有縮排 ```csharp= using System; namespace circle {class Program{static void Main(string[] args){ Console.WriteLine("HelloWorld!"); } } } ``` ##### 2. 有縮排 ```csharp= using System; namespace circle { class Program { static void Main(string[] args) { Console.WriteLine("HelloWorld!") } } } ``` :::info **雖然上面兩個程式執行後的結果相同,但是可以很明顯地看到,第二個比第一個來的易讀許多** ::: --- ## 2.資料型態 & 變數 ### **Example**:如果以10為半徑,要如何計算出圓面積? #### ==此時我們可以將此問題拆成三個部分來看== 1. #### Input :要怎麼儲存這筆資料 (將 10 儲存下來) 2. #### Algorithm:要怎麼計算出結果 3. #### Output :結果如何呈現 ```csharp= using System; namespace circle { class Program { static void Main(string[] args) { //data int r = 10; double A; //algorithms; A = r * r * 3.14; //output Console.WriteLine(A); } } } ``` :::info :bulb:在這段程式中,我們使用了兩種資料型態:==int== , ==double== ::: --- ### **變數 (Variable)** #### **概念:** * ##### 變數就像一個箱子,專門拿來存放東西 * ##### 每一個變數,都必須要有一個型態 (type) #### **宣告 (Declaration):** 1. ##### 首先我們取一個變數的名稱,假設是 A 2. ##### 接著我們要幫 A 找能夠儲存我們資料的箱子 ```csharp int A ; //變數名稱為 A 且只能儲存 int 類型資料 ``` > 此時我們將 A 宣告成一個 int 的型態 #### **記憶體位置:** ##### 你可能會想說:「現在雖然是有箱子沒錯,可是要把箱子放在哪裡呢?」 ##### 那當然是記憶體噜~ ![](https://i.imgur.com/5VgVg20.png) * ##### 以我們剛剛的 int A 來看,A代表的意義就是箱子的位置 ( 類似箱子上貼有標籤 A ) * ##### 上圖中的 0x000abc01 是==十六進位碼== -- 表示那個箭頭處的位置 * ##### 如果我們此時將整數 10 賦值到 A,則就代表著我們在 0x000abc01 那邊的 int 箱子裡,放了整數 10 進去 * ##### 上圖過程的程式碼如下 ```csharp int A = 10; ``` :::info C# 中的**等號**表示==將右邊賦值到左邊==,例如 int A = 10,此時 A 的值為 10 ::: #### **命名規定:** 1. ##### 不能以數字開頭 2. ##### 不能是 C# 中的關鍵字,例如:using、class、int、string 3. ##### 名字中間不能以空格隔開 4. ##### 不能有任何的運算符號,例如:+ , - , * , / | **加法** | **+** | |:----------:|:-----------------:| | **減法** | **-** | | **乘法** | **\*** | | **除法** | **/** | | **取餘數** | **%** | | **X = X ± 1** | **X±±** | | **開根號** | **Math.Sqrt(值)** | --- ### **資料型態 (Data types)** ##### **在資料型態中主要分為三大類:** ##### ==**原生類型 (Primitive type)、參考類型 (Reference types)、指標類型 (Pointer types)**== #### **1. 原生類型 (Primitive types)** ##### **(1) 布林值:** | 類型 | 大小 | |:-------:|:-------------------------:| | **bool** | **1 bit** | ##### **(2) 數值:** ###### a. 整數類型 | 類型 | 大小 | |:---------:|:-----------:| | **short** | **16 bits** | | **byte** | **8 bits** | | **int** | **32 bits** | | **long** | **64 bits** | | **char** | **8 bit** | :::info **char** 通常都會配合字碼表來處理字元,==本質上還是處理數字== ::: ###### b. 浮點數類型類型 | 類型 | 大小 | |:----------:|:-----------:| | **float** | **32 bits** | | **double** | **64 bits** | | **decimal**| **128 bits** | | :::info **double** 能夠比 **float** 更加精確,但是相對的==運算速度較慢== ::: :::info **decimal** 的儲存大小雖然大,但是所含的範圍卻沒有前兩者高,目的是為高精確 ::: #### **2. 參考類型 (Reference types)** | 類型 | 功能 | |:----------:|:-----------:| | **object** | **可以用來裝箱、拆箱** | | **dynamic** | **可以自動判斷類型** | | **string**| **處理字串** :::info 將值轉換成 **object** 類型稱為「**裝箱**」,反之則為「**拆箱**」 ::: #### **2. 指標類型 (Pointer types)** | 類型 | 功能 | |:----------:|:-----------:| | **int*** | **用來儲存位置** | | **char*** | **用來儲存位置** | >補充: >資料型態的轉換 [https://www.runoob.com/csharp/csharp-type-conversion.html](https://) --- ### **==小試身手==** #### 1. 製作一個 BMI 計算器,輸入「身高」與「公斤」即可獲得 BMI #### 2. 哈囉 -- 輸入一個字串,輸出 Hello, 字串 >提示:讀取輸入用 Console.ReadLine(),字串的資料類型為 string --- # 第五週 ## 1. 基本輸入、輸出 ### **輸出 (Output)** #### Example: ```csharp= using System; namespace input { class Program { static void Main(string[] args) { int num = 5; // Output Console.WriteLine("Hello World!"); // 純字串 Console.WriteLine(10); // 數字 Console.WriteLine(num); // 變數名 Console.WriteLine("Hello" + " " + "World!"); // 字串組合 Console.WriteLine("num: " + num); // 字串與變數組合 } } } ``` #### 執行結果: ![](https://i.imgur.com/IoKvRzp.png) ### **輸入 (Input)** #### Example: ```csharp= using System; namespace output { class Program { static void Main(string[] args) { // input string str = Console.ReadLine(); // 將輸入的 "字符" 賦值給該變數的儲存空間 Console.WriteLine(str); // 輸出變數 Console.WriteLine(Console.ReadLine()); //直接將輸入的東西打印出來 int num1 = int.Parse(Console.ReadLine()); //處理能力較低 Console.WriteLine(num1); int num2 = Convert.ToInt32(Console.ReadLine()); //處理能力較高 Console.WriteLine(num2); } } } ``` #### 執行結果: ![](https://i.imgur.com/83tjNMV.png) ### 比較 int.Parse() 與 Convert.ToInt32 的差異 #### 剛剛上面有說到 ==int.Parse() 的處理能力會比 Convert.ToInt32() 的處理能力還來的低==,簡單舉兩個例子來驗證。 1. **Convert.ToInt32(null)** 會==回傳 0==,但是 **int.Parse(null)** 會直接==報格式錯誤==。 3. **Convert.ToInt32()** 如果接收到小數,會採取==四捨六入==,如果是小數點後是 5 的話,則取距離最近的偶數整數,但是如果是 **int.Parse()** 接收到小數,則是==報格式錯誤==。 #### Example 1-1: ```csharp= using System; namespace output_IntParse { class Program { static void Main(string[] args) { // int.Parse() int num = int.Parse(null); // 接收 null 值 Console.WriteLine(num); } } } ``` #### 執行結果: ![](https://i.imgur.com/DISUFGs.png) #### Example 1-2: ```csharp= using System; namespace ConvertToInt { class Program { static void Main(string[] args) { // Convert.ToInt32() int num = Convert.ToInt32(null); // 接收 null 值 Console.WriteLine(num); } } } ``` #### 執行結果: ![](https://i.imgur.com/5A5pjgM.png) #### Example 2-1: ```csharp= using System; namespace output_IntParse { class Program { static void Main(string[] args) { // int.Parse() int num = int.Parse(4.2); // 接收小數 Console.WriteLine(num); } } } ``` #### 執行結果: ![](https://i.imgur.com/RMEY2Az.png) #### Example 2-2: ```csharp= using System; namespace ConvertToInt { class Program { static void Main(string[] args) { // Convert.ToInt32() int num1 = Convert.ToInt32(4.2); // 輸出 4 Console.WriteLine(num1); int num2 = Convert.ToInt32(4.6); // 輸出 5 Console.WriteLine(num2); int num3 = Convert.ToInt32(4.5); // 輸出 4 Console.WriteLine(num3); int num4 = Convert.ToInt32(5.5); // 輸出 6 Console.WriteLine(num4); int num5 = Convert.ToInt32(-1.5); // 輸出 -2 Console.WriteLine(num5); } } } ``` #### 執行結果: ![](https://i.imgur.com/RWiba7T.png) :::info :bulb: 初學的時候其實不用太計較這個,先選一個好記的做就好瞜,當然我比較推薦 **Convert**~ ::: --- ## 2. 條件運算式 (Conditional statements) ### 關係運算子 (Relational Operators) | **相等** | **==** | |:----------:|:-----------------:| | **不等於** | **!=** | | **大於** | **>** | | **小於** | **<** | | **大於等於** | **>=** | | **小於等於** | **<=** | ### 邏輯運算子 (Logical Operators) | **且** | **&&** | |:----------:|:-----------------:| | **或** | **\|\|** | | **非** | **!** | ### **if 語句** -- 當條件成立時執行 #### Example: ```csharp= using System; namespace If { class Program { static void Main(string[] args) { // if statement if(1 == 1){ Console.WriteLine("1 = 1 成立"); } if(1 == 2){ Console.WriteLine("1 = 2 成立"); } if(1 != 2){ Console.WriteLine("1 = 2 不成立"); } if(1 == 1 && 2 == 2){ Console.WriteLine("1 = 1 且 2 = 2 成立"); } if(1 == 1 || 1 == 2){ Console.WriteLine("1 = 1 或 1 = 2 成立"); } } } } ``` #### 執行結果: ![](https://i.imgur.com/oY7flUm.png) >1. 從執行結果可以知道,只有條件成立的時候才會執行 if 所框出範圍的程式 >2. if 後面的括號內放下條件 >3. 條件內通常會用到 ==邏輯運算子== 與 ==關係運算子== :::info 前情提要:之前有說過 { } 代表著==劃定範圍==,所以在 if 語句的範圍內才會受條件的限制 ::: ### **if else 語句** -- 當條件成立時執行 if 範圍,否則執行 else 範圍 #### Example: ```csharp= using System; namespace If_else { class Program { static void Main(string[] args) { // if else statement if(1 == 2){ Console.WriteLine("1 = 2 成立"); }else{ Console.WriteLine("1 = 2 不成立"); } if(1 == 1){ Console.WriteLine("1 = 1 成立"); }else{ Console.WriteLine("1 = 1 不成立"); } if(1 == 1 && 1 == 2){ Console.WriteLine("1 = 1 且 1 = 2 成立"); }else{ Console.WriteLine("1 = 1 且 1 = 2 不成立"); } } } } ``` #### 執行結果: ![](https://i.imgur.com/vQ1SeOz.png) >從結果可以知道,當 **if** 內的條件不成立時,則會運行 **else** 範圍內的程式,當 **if** 內的條件成立時,則只會執行 **if** 範圍內的程式。 ### **if else if 語句** -- 巢狀結構 #### Example: ```csharp= using System; namespace If_else_if { class Program { static void Main(string[] args) { // if else if statement if(1 == 2){ Console.WriteLine("1 = 2 成立"); }else if(1 == 3){ Console.WriteLine("1 = 3 成立"); }else if (1 == 4){ Console.WriteLine("1 = 4 成立"); }else{ Console.WriteLine("你開出的條件都不成立啦 =.="); } } } } ``` #### 執行結果: ![](https://i.imgur.com/b5eTxST.png) > 經過一層一層的判斷,最後得知前面的每個條件皆不成立 ### **switch 語句** -- 事件判斷 #### Example: ```csharp= using System; namespace If_else_if { class Program { static void Main(string[] args) { // switch statement Console.WriteLine("你可以告訴我今天星期幾嗎? (請輸入阿拉伯數字)"); int input = Convert.ToInt32(Console.ReadLine()); switch(input) { case 1: Console.WriteLine("謝謝你告訴我今天是星期一"); break; case 2: Console.WriteLine("謝謝你告訴我今天是星期二"); break; case 3: Console.WriteLine("謝謝你告訴我今天是星期三"); break; case 4: Console.WriteLine("謝謝你告訴我今天是星期四"); break; case 5: Console.WriteLine("謝謝你告訴我今天是星期五"); break; case 6: Console.WriteLine("謝謝你告訴我今天是星期六"); break; case 7: Console.WriteLine("謝謝你告訴我今天是星期日"); break; default: Console.WriteLine("痾...請問哪來的星期 " + input); break; } } } } ``` #### 執行結果: ![](https://i.imgur.com/9IjpYXr.png) ![](https://i.imgur.com/lQZh2jD.png) >可以針對不同的事件,做出相應的應對,break 代表當前的事件的結束點。 --- - 本單元索引 [ToC] - 參考資料 1.https://apcs.csie.ntnu.edu.tw/index.php/info/environment/ 2.https://learn.microsoft.com/zh-tw/dotnet/core/tutorials/with-visual-studio-code?pivots=dotnet-6-0 3.https://ithelp.ithome.com.tw/articles/10213373 4.https://ithelp.ithome.com.tw/articles/10213219