[Notes] Go/Golang 基本語法 Part1

Haren Lin
7 min readJul 7, 2021

--

Gopher

實習開始時,有先跟 Mentor 詢問之後有可能會用到什麼程式語言,於是就開始我的 Go 之旅!以下紀錄我學習 Go 的筆記,也當作日後複習使用。

對於 Go 語言的特色,首先要知道以下幾點:
(1) Code runs really fast.
(2) Garbage Collection (GC)
(3) Simpler Objects (Not using class)
(4) Concurrency is efficient. (Go-routine)

在學習任何程式語言剛開始時,不免俗的要來個 Hello World!

對於每個獨立的 Go 程式碼而言,其實外表長得跟 C/C++ 很像,透過一個主函式包裝起來,而 import 就跟 include 的概念一樣,引入函示庫。

至於要如何執行 Go 的程式碼在 Terminal 上,其實很簡單:

go run file-name.go

變數 Variable

(1) 變數宣告 Variable Declaration

在 Go 裡面,我們會用 var 來定義變數,跟其他語言不同的是,必須將型態宣告寫在後面。

輸出結果為:0 0 0 false false false。為什麼我們沒有賦予變數起始值,那他會存有看起來很正常的數值,而不是像 C/C++ 一樣是殘值呢?因為在 Go 裡面,當你沒有給他起始值,他會 implicit 給予變數一個零值,以 int 來說就是給 0,以 bool 形態來說就是給 False。

(2) 初始化變數 Variable Initialization

Formula: var [variable_name] [variable_type] = [init_value]

定義變數時可以直接賦予起始值,變數與其被賦予的值要互相對應。如果有初始化的話,型別就可以省略,變數會直接取用起始值的類型。以下範例輸出結果為:1 2 3 true false Haren。

定義字串時,如果我必須定義多行字串,可以使用反引號 `` 來定義

str1 := `IronMan,  
his name is Tony Stark,
and he is my favorite hero.`

(3) 短變數宣告 Variable Short Assignment

在「函數」中 := 簡潔賦值語句在明確類型的地方,可以替代 var 定義。

Inside a function, the := short assignment statement can be used in place of a var declaration with implicit type. Outside a function, every statement begins with a keyword (var, func, and so on) and so the :=construct is not available.

在變數宣吿有一點值得注意的是:在 Go 語言中命名開頭的大小寫是有用處的,在函式以外的地方宣告變數、方法、結構等等,只要是名稱開頭是大寫的,表示可以被匯出 (exported),意思就是可以被其他的 package 使用;反之名稱開頭是小寫的話,就只有目前的 package 可以使用。

P.S. 為了保持程式碼的乾淨,如果宣告了一個變數但是卻沒有使用,Go 連編譯都不會讓你編譯。如果引入了一個函式庫但是卻沒有使用,Go 也一樣不會讓你編譯。

常數 Constant

Go 常數的宣告和變數差不多,只是把關鍵字 varconst

// 單一宣告 
const pi = 3.141592
const e = 2.718281
// 多重宣告
const (
pi = 3.141592
e = 2.718281
)

迴圈 For Loop

(1) 在 Go 裡面,迴圈的表示只有一種,就是 for,不存在 while 或是 do … while 的架構。而 for 迴圈除了強制沒有小括號 () 之外,它外觀跟 C/C++ 的迴圈是一樣的,而大括號 {} 是必須的。有一點可以需注意:Go 沒有提供 ++i 之類的語法。請見以下範例,輸出結果為45。

(2) 此外,跟 C/C++ 中一樣,可以讓前置與後置語句為空。請見以下範例,輸出結果為1024。

(3) 你也可以把分號都去掉,將形成用 for 表示的 while。請見以下範例,輸出結果為1024。

流程控制

(1) If-Else

if 可以在條件內容中執行簡單的語句,此外在 if 計算的東西,也能夠在 else 中被使用。輸出結果為: 9 < 10 以及 27 >= 20。

(2) Switch-Case

Switch 是比 if 更有閱讀性的控制結構,跟 C 語言不同的是他不需要 break 來跳出。注意,如果使用 fallthrough 關鍵字,會執行下一個 Case。另外,Switch 後的陳述不是必須的,你可以寫 case 裡面,允許 case 帶條件式。最後,每個 case 結束後不用再寫 break,Go 的 case 執行完就會直接離開 switch block,比起 C/C++ 算是很棒的改良。

請看下方舉例,choose 與 anotherChoose 的比較。

陣列 Array

宣告陣列,只需在變數宣告後面多加上 [] 即可,裡面填寫宣告的陣列大小。

想要知道某個陣列的大小,可以使用 len(array_name) 取得其長度。此外,你可以把陣列做全部與部分初始化,未被初始化的部分會賦予零值。

此外,如果陣列有設定初始值時,可以省略陣列長度的部分用 ... 取代,系統會依照初始值的數量,幫我們建立一個相同長度的陣列。

arr := [...]string{"Haren Lin", "Dr.T", "Gryffin"}  

另外 for 迴圈有種內建的寫法可以 traverse 每個 element,就是用 range,他預設會有兩個回傳值,一個是 key 一個是 value。

切片 Slice

在建立陣列的時候要指定整個陣列的大小,但,當我們今天如果不知道要多大怎麼辦?陣列可以不輸入元素大小嗎?答案是可以!他是 Slice。

Slice 有兩種數值,一個是 capacity 一個是 length。這兩個有什麼不同呢?其實容量 capacity 就是最大能裝多少,而長度 length 不能超過容量。

我們能利用別的 Slice / Array 來建立 Slice,[low : high] 這個方法來參考。

arr := [5]float64 {1, 2, 3, 4, 5} 
x := arr[0:5]

需要特別注意的點是 high 表示的是結束的點,而不是它的元素位置。以上例而言 arr[0:5] 其實是指 [1,2,3,4,5] ,如果是 arr[1:4] 則是 [2,3,4]。在某些情況下 low 跟 high 是可省略,像 arr[0:5] 可省略成 arr[:5];如果省略成 arr[0:] 則是相當於 arr[0: len(arr)] ;當然也可以省略成 [:] ,它相當於 arr[0:len(arr)]。

除此之外,也可以直接宣告 Slice。

另外,如何動態宣告 Slice?

// 動態宣告一個slice x 裡面存放 float64 的數值,且長度為5,容量為10
x := make([]float64, 5, 10)

結束宣告的部分後,Slice 有兩個必學的函式:
(1) Append 新增

當我們要動態增加資料時,可以用 append( ) 來附加一個新元素,如果現有空間不足時,切片就會自動擴增容量。

從上面的結果可以發現,每次執行 append 時候都因容量不足而擴增,且以目前容量 2 倍數進行擴增。

(2) Copy 複製:可以將一個 Slice A 的值複製到另外一個 Slice B,但無法超過容量限制。以下範例將容量為 3 的 slice 的數值 1, 2, 3 複製到 slice2 ,但是 slice 2 的容量只有 2,所以實際上 slice2 的值是 1, 2。

函式 Function

參考資料 / Reference

1. A Tour of Go
2. Golang 30 天
3. Golang Crash Course
4. Learn Go Programming — Golang Tutorial for Beginners

This article will be updated at any time! Thanks for your reading. If you like the content, please click the “clap” button. You can also press the follow button to track new articles at any time. Feel free to contact me via LinkedIn or email.

--

--

Haren Lin
Haren Lin

Written by Haren Lin

MSWE @ UC Irvine | MSCS @ NTU GINM | B.S. @ NCCU CS x B.A. @ NCCU ECON | ex-SWE intern @ TrendMicro

No responses yet