在上一節(聊聊Go的工做空間),提到了Go包,這一節,咱們就來仔細講講。git
Go語言中的包,實際上是一種組織代碼的方式。Go 的程序都會組織成若干組文件,而每組文件被稱爲一個包。go安裝完成以後,在GOROOT/src
目錄,自帶了各類各樣的包,例如經常使用的io
包、fmt
包、math
包等。咱們就來分析下io
包,看看go內置的包是如何組織代碼的。 github
io
包的目錄結構,分別打開
io.go
、
multi.go
和
pipe.go
,你會發如今文件非註釋的第一行都聲明瞭
package io
。沒錯,這三個源文件都屬於同一個go包--
io
包。到這裏,其實已經很明白了,所謂的go包就是計算機中的目錄,通俗點講就是文件名。go語言就是這樣經過它們進行目錄結構和文件組織的。在
io
包目錄下,其實還有個
ioutil
包,感興趣的同窗能夠打開
ioutil
目錄下的文件,一探究竟。(以
_test.go
結尾的測試文件,忽略)
使用關鍵字--package
。和go文件所在目錄同名,這是go包命名的最大原則,其次還應該作到簡潔、清晰且全小寫。這種命名方式有利於開發時書寫包名,查找和定位。例如,上面提到的 io
包、ioutil
包,命名都很簡短且清晰。所屬io
包的三個文件,在文件開頭都聲明瞭package io
。分佈式
使用關鍵字--import
。使用一個包,必須先將包導入(無論是go內置包仍是本身寫的包)。例如:函數
// 導入單個包
import "fmt"
複製代碼
// 使用go語言提供的導入快,導入多個包,每一個包獨佔一行
import (
"fmt"
"io/ioutil"
"github.com/Seekload/stringutil"
)
複製代碼
import
告訴編譯器到磁盤的哪裏去找想要導入的包。其實,上面導入fmt
、io/ioutil
和github.com/Seekload/stringutil
是一個相對路徑,編譯器會使用 Go 環境變量(GOROOT
和GOPATH
)設置的路徑,經過引入的相對路徑來查找磁盤上的包。例如io/ioutil
,編譯器最終會在GOROOT/src/io/ioutil
路徑下查找到ioutil
包。相似的,會在GOPATH/src/github.com/Seekload/stringutil
路徑下查找到stringutil
包。提一點:編譯器在查找的時候,會優先在GOROOT
路徑下查找,其次,在GOPATH
下查找,查找無果以後會報編譯錯誤。 導入包完成以後,就可使用包提供的常量、函數等,例如:工具
fmt.Println();
ioutil.ReadDir();
複製代碼
某一天,你在瀏覽github
,發現一個函數豐富的包,想在本身的項目上使用,目前,你想到的引用辦法可能就是直接將包clone
到本地,而後放到GOPATH/src/
目錄,開始引用。其實,有一種更簡便的方式,就是遠程導入--使用go get
命令。這種導入的前提就是,包託管在一個分佈式的版本控制系統上,好比Github等,而且是Public的權限。 我在GitHub上就有一個github.com/Seekload/stringutil
包(使用本身的域名做爲包名一部分是爲了不包名重複,GitHub上的包太多了~),你們能夠跟着我實操一下: 你們看下,個人工做空間目前是這樣的, post
GOPATH
執行
go get github.com/Seekload/stringutil
導入遠程包以後:
stringutil
包已經下載到工做空間,而且已經生成靜態庫文件
stringutil.a
,說明對包已進行過編譯和安裝。
注意:
go get
工具能夠遞歸獲取依賴包,若是
github.com/Seekload/stringutil
也引用了其餘的遠程包,也能夠一併下載下來。 好了,如今就能夠在
hello.go
中導入包了
package main
import (
"fmt"
"github.com/Seekload/stringutil"
)
func main() {
fmt.Println(stringutil.Reverse("!oG ,daolkeeS"))
}
複製代碼
執行編譯安裝go install hello/
,生成可執行文件hello
學習
import
支持多個包導入,若是導入的包出現重名,該怎麼辦?別擔憂,Go開發團隊已經考慮到這個問題了,提供給咱們的方法就是,對導入的包從新命名--即命名導入:在 import
語句給出的包路徑的左側定義一個名字,將導入的包命名爲新名字。看代碼:測試
package main
import (
"fmt"
myfmt "github.com/Seekload/stringutil/fmt"
)
func main() {
fmt.Println()
myfmt.Println()
}
複製代碼
若是,代碼裏導入了一個沒有用到的包,Go編譯器不會告警,而是直接編譯失敗,並拋出一個錯誤。Go 開發團隊認爲,導入的包應該被使用。否則,無用的包過多,會使代碼變得臃腫且管理繁瑣。不過,有時,咱們須要導入一個包,可是又用不到,怎麼辦?不要緊,Go提供了空白標識符 _
來重命名這個包導入。spa
package main
import (
"fmt"
_ "github.com/Seekload/stringutil/fmt"
)
複製代碼
這裏提到了下劃線字符_
,之後還會接觸到。.net
下劃線字符
_
稱爲空白標識符,做用:拋棄不想繼續使用的值,如給導入的包賦予一個空名字,或者忽略函數返回的你不感興趣的值。
關於Go包就講解到這裏。
原創文章,若需轉載請註明出處!
歡迎掃碼關注公衆號「Golang來啦」或者移步 seekload.net ,查看更多精彩文章。
公衆號「Golang來啦」給你準備了一份神祕學習大禮包,後臺回覆【電子書】領取!