[Introduction]Go基础:package/modules/main

3,339 阅读3分钟

一.package

1.实例

Go使用包来组织源码,所有语法的可见性均定义在package这个级别,一般会有一个test文件用于单元测试

每一个包中的go文件可以互相引用其中方法

假设项目顶层目录为./top,在top下创建main.go文件作为程序执行入口(./top/main.go),包名必须是package main

假设有功能A和B分别放在./top/A/a.go./top/B/b.go下,分别为package A和package B:

// a.go
package A

func a {
    ...
}
// b.go
package B

func b {
    ...
}

在main.go中引入a和b函数:

//main.go
package main

import (
    "top/A"    // import的是目录名
    "top/B"    // import的是目录名
)

func main() {
    A.a()      // 这里应用的是包名
    B.b()
}

2.包名/路径/目录名/文件名的关系

1.import导入的是相对路径,非package名!

2.习惯上将package名和目录名保持一致,如实例中package A尽量在./top/A文件夹下

3.代码中引用包方法/对象/变量时,如调用package A中的a函数,使用A.a而非目录名

4.同一目录下,所有源文件必须使用相同的包名,一个文件夹下只能有一个package;如果多个文件夹下有同名package,其实只是彼此无关的package,如果需要同时使用不同目录下的同名package,import时需要为每个目录指定package别名:

5.同一package下不同文件间可以直接调用

6.大写字母开头的变量方法暴露到包外,包内大小写随意

7.多个go文件在main包下是无法相互调用的,需要使用go run *.go命令

import (
    A1 "top/mid1/A"   // package A
    A2 "top/mid2/A"   // package A
)

3.在package中/间相互引用

Go语言import导入包——在代码中使用其他的代码

见2.6

4.可见性

可见性只针对包,而不针对文件

使用下划线来引入该包,并不使用包内函数,而是仅仅只调用了包内的init()函数,在引入时调用执行init()

二.modules

go mod的使用

三.main函数/init函数

若在包中定义init()函数,则该函数会在包引入时执行

main函数和init函数:

相同点:两个函数在定义时不能有任何的参数和返回值。该函数只能由 go 程序自动调用,不可以被引用。

不同点:init 可以应用于任意包中,且可以重复定义多个。main 函数只能用于 main 包中,且只能定义一个。

函数执行顺序:

在 main 包中的 go 文件默认总是会被执行。对同一个 go 文件的init( )调用顺序是从上到下的

对同一个 package 中的不同文件,将文件名按字符串进行“从小到大”排序,之后顺序调用各文件中的init()函数

对于不同的 package,如果不相互依赖的话,按照 main 包中 import 的顺序调用其包中的 init() 函数

如果 package 存在依赖,调用顺序为最后被依赖的最先被初始化,例如:导入顺序 main –> A –> B –> C,则初始化顺序为 C –> B –> A –> main,一次执行对应的 init 方法。main 包总是被最后一个初始化,因为它总是依赖别的包

避免出现循环 import,例如:A –> B –> C –> A。一个包被其它多个包 import,但只能被初始化一次

参考链接:

Go语言基础进阶教程

Go包名规则

彻底理解Go包的概念