英文:
What does an underscore in front of an import statement mean?
问题
在这段来自go-sqlite3的代码中:
import (
"database/sql"
"fmt"
_ "github.com/mattn/go-sqlite3"
"log"
"os"
)
import
语句中的下划线(underscore)代表匿名导入。匿名导入意味着导入的包将被编译器加载,但在代码中无法直接使用该包的标识符。在这种情况下,_ "github.com/mattn/go-sqlite3"
表示导入了github.com/mattn/go-sqlite3
包,但在代码中没有直接使用该包的标识符。通常情况下,这样的导入用于执行包的初始化操作,而不需要在代码中直接使用该包。
英文:
In this code from go-sqlite3:
import (
"database/sql"
"fmt"
_ "github.com/mattn/go-sqlite3"
"log"
"os"
)
what does the underscore in the import
statement mean?
答案1
得分: 324
这是用于仅导入一个包以获取其副作用的情况。
根据Go规范:
要仅为了其副作用(初始化)而导入一个包,请使用下划线作为显式包名:
import _ "lib/math"
在sqlite3中
在go-sqlite3的情况下,下划线导入用于在init()
函数中注册sqlite3
驱动程序作为数据库驱动程序的副作用,而不导入任何其他函数:
sql.Register("sqlite3", &SQLiteDriver{})
一旦以这种方式注册,就可以在代码中使用sqlite3与标准库的sql
接口一起使用,就像下面的示例一样:
db, err := sql.Open("sqlite3", "./foo.db")
英文:
It's for importing a package solely for its side-effects.
From the Go Specification:
> To import a package solely for its side-effects (initialization), use the blank identifier as explicit package name:
>
> go
> import _ "lib/math"
>
In sqlite3
In the case of go-sqlite3, the underscore import is used for the side-effect of registering the sqlite3
driver as a database driver in the init()
function, without importing any other functions:
sql.Register("sqlite3", &SQLiteDriver{})
Once it's registered in this way, sqlite3 can be used with the standard library's sql
interface in your code like in the example:
db, err := sql.Open("sqlite3", "./foo.db")
答案2
得分: 63
虽然其他答案已经完全描述了这个问题,但对于“Show me The Code”的人来说,这基本上意味着:创建包级变量并执行该包的init
函数。
以及(如果有的话)该包导入的包的包级变量和init
函数的层次结构。
一个包在没有被实际调用的情况下唯一能产生的副作用是创建包级变量(公共或私有)并在其init
函数内部使用。
注意:有一个技巧可以在init
函数之前运行一个函数。我们可以使用包级变量通过使用该函数进行初始化。
func theVeryFirstFunction() int {
log.Println("theVeryFirstFunction")
return 6
}
var (
Num = theVeryFirstFunction()
)
func init() { log.Println("init", Num) }
英文:
While other answers described it completely, for "Show me The Code" people, this basically means: create package-level variables and execute the init
function of that package.
And (if any) the hierarchy of package-level variables & init
functions of packages that, this package has imported.
The only side effect that a package can make, without being actually called, is by creating package-level variables (public or private) and inside it's init
function.
Note: There is a trick to run a function before even init
function. We can use package-level variables for this by initializing them using that function.
func theVeryFirstFunction() int {
log.Println("theVeryFirstFunction")
return 6
}
var (
Num = theVeryFirstFunction()
)
func init() { log.Println("init", Num) }
答案3
得分: 23
以下是要翻译的内容:
https://golang.org/doc/effective_go.html#blank
这要么是一个正在进行的工作,要么是为了副作用而导入的。在这种情况下,我认为它是为了副作用而导入的,正如文档中所描述的。
英文:
https://golang.org/doc/effective_go.html#blank
It's either a work in progress, or imported for side effects. In this case, I believe it's for the side effects, as described in the doc.
答案4
得分: 6
假设你有一个Animal包。你的主文件想要使用这个Animal包来调用一个名为Speak的方法,但是有许多不同类型的动物,每个动物都实现了自己的通用Talk方法。所以假设你想要调用Animal包中实现的Speak方法,该方法在内部调用了每个动物包中实现的Talk方法。在这种情况下,你只需要做一个import _ "dog",这实际上会调用dog包中定义的init方法,该方法实际上会向Animal包注册一个Talk方法,而Animal包也会导入它。
英文:
Let's say you have an Animal package. And your main file wants to use that Animal package to call a method called Speak but there are many different types of animals and each animal implemented their own common Talk method. So let's say you want to call a method Speak implemented in the Animal's package which internally calls Talk method implemented in each of the animal's package. So in this case you just want to do an import _ "dog" which will actually call the init method defined inside the dog package which actually registers a Talk method with the Animal package which it too imports.
答案5
得分: 1
作为我在Go语言中的新手,这个定义使它更清晰:
下划线是Go语言中的一个特殊字符,它充当空容器的角色。由于我们导入了一个包但没有使用它,Go编译器会对此发出警告。为了避免这种情况,我们将该包的引用存储在_中,Go编译器将简单地忽略它。
有时,使用下划线对包进行别名处理,虽然看起来没有任何作用,但却非常有用,特别是当你想要初始化一个包但不使用它时。
英文:
As I'm new in Go, this definition made it more clear:
> Underscore is a special character in Go which acts as null container. Since we are importing a package but not using it, Go compiler will complain about it. To avoid that, we are storing reference of that package into _ and Go compiler will simply ignore it.
Aliasing a package with an underscore which seems to do nothing is quite useful sometimes when you want to initialize a package but not use it.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论