--- title: 關於函式的一些事情 tags: C++ --- # main函式 ### 函式要先定義 c++編譯器在執行時**唯一會自動呼叫**的是 **``main 函式``** 所以如果有在 main 裡呼叫其他函式的話 一定要在main之前定義該函式 ```cpp= #include <iostream> using namespace std; int main(void){ test(); return 0; } void test(void){ cout<<"Testing!"; } ``` 上方就會報錯 ``` 正在開始建置... "C:\Program Files\mingw64\bin\g++.exe" -fdiagnostics-color=always -g C:\Users\SUMESIN\Desktop\C++\things_aboout_function.cpp -o C:\Users\SUMESIN\Desktop\C++\things_aboout_function.exe C:\Users\SUMESIN\Desktop\C++\things_aboout_function.cpp: In function 'int main()': C:\Users\SUMESIN\Desktop\C++\things_aboout_function.cpp:4:5: error: 'test' was not declared in this scope 4 | test(); | ^~~~ 建置已完成,但發生錯誤。 ``` 不過定義時可以不用寫很詳細 只要定義**回傳值跟參數**的型態就好 ```cpp= #include <iostream> using namespace std; void test(int); int main(void){ test(); return 0; } void test(int a = 10){ cout<<"Testing!"<<a; } ``` >圖中有使用**預設參數** ### main的回傳值 在各個系統中 對 main 函式的回傳值有不同的動作 只有唯三結果才會一樣 其中一個就是代表函式順利執行的 ```0``` 而且就算不寫回傳值 實際上會在底下進行例外處裡 執行成功的話就傳回 ```0``` ```cpp= int main(void){ test(); } ``` # 傳參呼叫&傳值呼叫 ### 傳值呼叫 ***Passed by value*** 編譯器做的事是把傳入的資料複製一份 賦值給函數定義時使用的參數 然而遇到大資料時就會出問題 ```cpp= #include <iostream> #include <string> using namespace std; void test(string); int main(void){ string a_large_string = "Pneumonoultramicroscopicsilicovolcanoconiosis"; test(a_large_string); return 0; } void test(string large_string){ cout<<large_string<<endl; cout<<"That's a large string"; } ``` ### 傳參呼叫 ***Passed by reference*** 遇到上面的問題時 就可以使用傳參呼叫 傳入的就是該**資料本身** 也就不會有複製的動作以及後續的問題 但是要注意的是 由於傳的是資料本身 所以在函式裡是會對資料進行修改的 ```cpp= #include <iostream> #include <string> using namespace std; void test(string&); int main(void){ string a_large_string = "Pneumonoultramicroscopicsilicovolcanoconiosis"; test(a_large_string); cout<<"but now, it's a small string"<<endl; cout<<a_large_string; return 0; } void test(string& large_string){ cout<<large_string<<endl; cout<<"That's a large string"<<endl; large_string = "pneumoconiosis"; } ``` 輸出為 ```= Pneumonoultramicroscopicsilicovolcanoconiosis That's a large string but now, it's a small string pneumoconiosis ``` 如果不希望資料被修改 只希望讀取的話 可以使用 ==**const reference**== ```cpp= #include <iostream> #include <string> using namespace std; void test(const string&); int main(void){ string a_large_string = "Pneumonoultramicroscopicsilicovolcanoconiosis"; test(a_large_string); cout<<"but now, it's a small string"<<endl; cout<<a_large_string; return 0; } void test(const string& large_string){ cout<<large_string<<endl; cout<<"That's a large string"<<endl; large_string = "pneumoconiosis"; } ``` 像上面就會報錯 :::danger 建置已完成,但發生錯誤。 ::: # inline 函式 可以在函式定義前加上 `inline` 關鍵字 告訴編譯器 在每次呼叫函式時 函式主體可以插入程式碼內 不用每次都執行正常的呼叫 這樣可以提高效率 ```cpp inline void test(string&); ``` 但實際上 inline 關鍵字的作用**僅僅只是建議而已** 事實上就算你跟編譯器說這函式可以 inline 他也只會接受建議 實際會不會執行由編譯器自行決定 :::warning 因為有關這方面的優化 在c++中是屬於**編譯器的工作** 就算不給 inline 關鍵字 編譯器也會照常自動決定函式是否需要 inline :::