在Golang中,使用`sql.NullFloat64`和`*float64`有什么区别?

huangapple go评论80阅读模式
英文:

Using sql.NullFloat64 vs *float64 in Golang?

问题

我正在使用gorm来定义我的数据库表结构。注意到gorm本身使用time.Time来表示created_at,而使用*time.Time来表示deleted_at。我猜这是因为deleted_at可能为NULL的情况。

我还注意到,在许多 Golang 的 ORM 中,他们使用sql.NullFloat64来存储可能是float64NULL的数据库值。为什么不直接使用*float64而是使用sql.NullFloat64?它们有什么区别?

type Geo struct {
    latitude  *float64
    longitude sql.NullFloat64
}

在这种情况下,latitudelongitude有什么区别?

英文:

I'm using gorm to define my db table schema. Noticed that gorm itself uses time.Time for created_at and *time.Time for deleted_at. I'm assuming this is because deleted_at has cases of being NULL.

I also noticed that for many Golang ORMs they use sql.NullFloat64 for storing db values that could be a float64 or NULL. Why not just use *float64 instead of sql.NullFloat64? What's the difference?

type Geo struct {
    latitude *float64
    longitude sql.NullFloat64
}
// What is the difference between latitude and longitude in this case?

答案1

得分: 6

根据Russ Cox的说法,使用NullString*string没有实质性的区别。他们认为人们可能希望使用NullString,因为它非常常见,可能比*string更清晰地表达了意图。但是两者都可以使用。

不过,我认为使用指针可能会给垃圾回收器(GC)增加一个要跟踪的对象。这可能取决于具体的使用情况。

在一些非常简单的代码中,使用-gcflags=-m进行构建时,逃逸分析确实会显示new(float64) escapes to heap(这里是我使用的虚拟代码:https://play.golang.org/p/K4sQaXyQKG)。

此外,在调试时,打印包含sql.NullSomething的结构体({value:{Float64:1 Valid:true}})比打印包含指针的结构体({value:0xc82000a420})更好看。

因此,我建议使用sql.Null*结构体。

英文:

From Russ Cox (biggest Go's contributor according to Github) : https://groups.google.com/forum/#!topic/golang-nuts/vOTFu2SMNeA

> There's no effective difference. We thought people might want to use NullString because it is so common and perhaps expresses the intent more clearly than *string. But either will work.

I'm thinking though that using a pointer might give the GC one more thing to track. It probably depends on the usage.

On some very simple code, using -gcflags=-m to build, the escape analysis does say that new(float64) escapes to heap (here is the dummy code I used: https://play.golang.org/p/K4sQaXyQKG).

Also, when debugging, printing a struct containing a sql.NullSomething ({value:{Float64:1 Valid:true}}) looks better than a struct containing a pointer ({value:0xc82000a420}).

So I'd recommend the usage of the sql.Null* structs.

huangapple
  • 本文由 发表于 2015年11月1日 09:46:08
  • 转载请务必保留本文链接:https://go.coder-hub.com/33458439.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定