作者选择了 多样性在技术基金作为 写给捐款计划的一部分接受捐款。
介绍
在现代程序中,重要的是在一个程序和另一个程序之间进行通信,无论是 Go程序检查用户是否可以访问另一个程序,一个 JavaScript程序获得在网站上显示的过去订单列表,还是一个 [Rust](https://en.wikipedia.org/wiki/Rust_(programming_language])程序从文件中读取测试结果,程序需要一种方式来提供其他程序的数据。然而,许多编程语言有自己的内部存储方式,其他语言无法理解。
许多现代编程语言包括在其标准库中将数据转换为和从JSON的方法,Go也是如此。通过使用Go提供的 coding/json
包,您的Go程序也将能够与任何其他可以使用JSON进行通信的系统进行交互。
在本教程中,您将开始创建一个使用编码/json
包来编码数据从地图
到JSON数据的程序,然后更新您的程序以使用结构
类型来编码数据,然后,您将更新您的程序来解码JSON数据到地图
,然后最终将JSON数据解码为结构
类型。
前提条件
要遵循本教程,您将需要:
- Go 版本 1.16 或更高版本已安装. 要设置此设置,请遵循操作系统的 How To Install Go教程。
- 熟悉 JSON,您可以在 An Introduction to JSON找到。
- 使用 Go struct 标签来定制
struct
类型的字段的能力. 更多信息可以在 How To Use Struct Tags in Go找到。 - 可选,了解如何在 Go 中创建日期和时间值。 您可以在 How To Use Dates and Times in Go阅读更多信息。 。
使用地图生成 JSON
Go 对 JSON 编码和解码的支持是由标准库的编码/json
包提供的。您从该包中使用的第一个函数是 json.Marshal
]函数。 Marshalling,有时也被称为 serialization,是将记忆中的程序数据转换为可以传输或存储到其他地方的格式的过程。 然后,json.Marshal``函数被用来将 Go 数据转换为 JSON 数据。
json.Marshal``函数接受一个界面类型作为将 marshal 值转移到 JSON,因此任何允许作为参数传输的值将作为结果返回 JSON 数据。 在
大多数 JSON 被表示为一个对象,具有字符串
密钥和各种其他类型的值,因此,在 Go 中生成 JSON 数据的最灵活的方式是使用字符串
密钥和接口
值将数据放入地图
。
要开始使用一个程序中的coding/json
包,你需要有一个程序目录. 在本教程中,你将使用一个名为项目
的目录。
首先,创建项目
目录并导航到它:
1mkdir projects
2cd projects
接下来,为您的项目创建目录. 在这种情况下,使用目录 jsondata
:
1mkdir jsondata
2cd jsondata
在jsondata
目录中使用nano
或您最喜欢的编辑器来打开main.go
文件:
1nano main.go
在main.go
文件中,您将添加一个main
函数来运行您的程序。接下来,您将添加一个map[string]interface{}
值,包含各种密钥和数据类型。
将下列行添加到 main.go:
1[label main.go]
2package main
3
4import (
5 "encoding/json"
6 "fmt"
7)
8
9func main() {
10 data := map[string]interface{}{
11 "intValue": 1234,
12 "boolValue": true,
13 "stringValue": "hello!",
14 "objectValue": map[string]interface{}{
15 "arrayValue": []int{1, 2, 3, 4},
16 },
17 }
18
19 jsonData, err := json.Marshal(data)
20 if err != nil {
21 fmt.Printf("could not marshal json: %s\n", err)
22 return
23 }
24
25 fmt.Printf("json data: %s\n", jsonData)
26}
在数据
变量中,你会看到每个值都有一个字符串
作为密钥,但这些密钥的值有所不同. 一个是int
值,另一个是bool
值,一个甚至是另一个map[string]interface{}
值,里面有[]int
值。
当您将数据
变量传输到json.Marshal
时,该函数将查看您提供的所有值,并确定它们的类型以及如何在 JSON 中表示它们。如果翻译中出现任何问题,则json.Marshal
函数将返回描述问题的错误
。如果翻译成功,则jsonData
变量将包含 marshalled JSON 数据的[]byte
。由于一个[]byte
值可以使用myString := string(jsonData)
或一个格式字符串中的%sverb [[LINK]
转换为string
值,您可以使用fmt.Printf
打印到屏幕上的 JSON 数据。
保存并关闭文件。
要查看您的程序的输出,请使用go run
命令并提供main.go
文件:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json data: {"boolValue":true,"intValue":1234,"objectValue":{"arrayValue":[1,2,3,4]},"stringValue":"hello!"}
在输出中,你会看到上层的 JSON 值是由围绕它的弯曲的轴承({}
)表示的对象.你在 data
中包含的所有值都存在.你还会看到 objectValue
的 map[string] interface{}
被翻译成另一个 JSON 对象,周围是 }{
,并且还包含了 arrayValue' 与
[1,2,3,4] 的数组值。
在 JSON 中编码时间
虽然编码/json
包不仅支持类型如string
和int
值,它还可以编码更复杂的类型,它支持的更复杂的类型之一是从 time
包的time.Time
类型。
<$>[注]
**注:**有关Go的时间
包的更多信息,请参阅如何在Go中使用日期和时间
(https://andsky.com/tech/tutorials/how-to-use-dates-and-times-in-go)。
若要看到此情况,请再次打开您的 main.go 文件,并使用time.Date
函数将time.Time
值添加到您的数据中:
1[label main.go]
2package main
3
4import (
5 "encoding/json"
6 "fmt"
7 "time"
8)
9
10func main() {
11 data := map[string]interface{}{
12 "intValue": 1234,
13 "boolValue": true,
14 "stringValue": "hello!",
15 "dateValue": time.Date(2022, 3, 2, 9, 10, 0, 0, time.UTC),
16 "objectValue": map[string]interface{}{
17 "arrayValue": []int{1, 2, 3, 4},
18 },
19 }
20
21 ...
22}
此更新将将UTC
时区中的2022年3月2日
日期和9:10:00 AM
时间分配给dateValue
键。
一旦您保存了更改,请使用与以前相同的运行
命令再次运行您的程序:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json data: {"boolValue":true,"dateValue":"2022-03-02T09:10:00Z","intValue":1234,"objectValue":{"arrayValue":[1,2,3,4]},"stringValue":"hello!"}
此时,在输出中,您将在 JSON 数据中看到一个dateValue
字段,使用使用 RFC 3339格式格式格式格式格式,该格式用于将日期和时间作为字符串
值传输。
在 JSON 中编码null
值
根据你的程序与哪些系统互动,你可能需要在你的JSON数据中发送null
值,Go的编码/json
包也可以为你处理。
要在 JSON 输出中添加几个null
值,请重新打开您的main.go
文件并添加以下行:
1[label main.go]
2...
3
4func main() {
5 data := map[string]interface{}{
6 "intValue": 1234,
7 "boolValue": true,
8 "stringValue": "hello!",
9 "dateValue": time.Date(2022, 3, 2, 9, 10, 0, 0, time.UTC),
10 "objectValue": map[string]interface{}{
11 "arrayValue": []int{1, 2, 3, 4},
12 },
13 "nullStringValue": nil,
14 "nullIntValue": nil,
15 }
16
17 ...
18}
您添加到数据的值有关键字表示它是字符串
值或int
值,但实际上代码中没有任何一个值使其成为这些值。
一旦您将更改保存到main.go
,请使用go run
运行您的程序:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json data: {"boolValue":true,"dateValue":"2022-03-02T09:10:00Z","intValue":1234,"nullIntValue":null,"nullStringValue":null,"objectValue":{"arrayValue":[1,2,3,4]},"stringValue":"hello!"}
现在在输出中,你会看到nullIntValue
和nullStringValue
字段包含一个JSONnull
值,这样你仍然可以使用map[string]interface{}
值将Go数据转换成预期字段的JSON数据。
在本节中,您创建了一个程序,可以将map[string]interface{}
值转化为 JSON 数据,然后,您将一个time.Time
字段添加到数据中,还包括了一对null
值字段。
虽然使用map[string] interface{}
来编辑 JSON 数据可以非常灵活,但如果您需要在多个地方发送相同的数据,也可以成为麻烦。如果您在代码中将这些数据复制到多个位置,则很容易意外误写一个字段名称,或者将错误的数据分配给一个字段。
使用结构生成 JSON
使用像 Go 这样的 静态键入语言的优点之一是,您可以使用这些类型来让编译器在您的程序中检查或执行一致性。 Go 的编码/json
包允许您通过定义一个结构
类型来代表 JSON 数据来利用此。
当你使用struct
来定义 JSON 数据时,你所期望的字段名称(而不是struct
类型名称本身)必须被导出,这意味着它们必须以大字母开始,例如IntValue
,或者encoding/json
包将无法访问字段来将它们翻译成 JSON。如果你不使用结构标签来控制这些字段的命名,则字段名称将被直接翻译,因为它们位于struct
上。使用默认名称可能是你在 JSON 数据中想要的,取决于你希望你的数据如何被组成。如果是这样的情况,你不需要添加任何结构标签。然而,许多 JSON 消费者使用字段名称格式如intalue
或int_value
,所以添加这些结构标签将允许
例如,假设您有一个名为IntValue
的结构
,您将其转换为 JSON:
1type myInt struct {
2 IntValue int
3}
4
5data := &myInt{IntValue: 1234}
如果您使用json.Marshal
函数将数据
变量转换为 JSON,您将获得以下值:
1{"IntValue":1234}
但是,如果您的 JSON 用户预计该字段将被命名为intValue
而不是IntValue
,那么您将需要一个方法来说encoding/json
。因为json.Marshal
不知道您希望该字段在 JSON 数据中被命名为什么,您将通过将结构标签添加到该字段来告诉它。
1type myInt struct {
2 IntValue int `json:"intValue"`
3}
4
5data := &myInt{IntValue: 1234}
这一次,如果将数据
变量转换为 JSON,则json.Marshal
函数将看到json
结构标签,并知道如何命名字段intValue
,因此您将获得预期的结果:
1{"intValue":1234}
现在,你会更新你的程序以使用你的JSON数据的结构
值。你会添加一个myJSON``结构
类型来定义你的顶级JSON对象,以及一个myObject``结构
来定义你的内部JSON对象为ObjectValue
字段。
打开main.go
文件,并进行以下更改:
1[label main.go]
2...
3
4type myJSON struct {
5 IntValue int `json:"intValue"`
6 BoolValue bool `json:"boolValue"`
7 StringValue string `json:"stringValue"`
8 DateValue time.Time `json:"dateValue"`
9 ObjectValue *myObject `json:"objectValue"`
10 NullStringValue *string `json:"nullStringValue"`
11 NullIntValue *int `json:"nullIntValue"`
12}
13
14type myObject struct {
15 ArrayValue []int `json:"arrayValue"`
16}
17
18func main() {
19 otherInt := 4321
20 data := &myJSON{
21 IntValue: 1234,
22 BoolValue: true,
23 StringValue: "hello!",
24 DateValue: time.Date(2022, 3, 2, 9, 10, 0, 0, time.UTC),
25 ObjectValue: &myObject{
26 ArrayValue: []int{1, 2, 3, 4},
27 },
28 NullStringValue: nil,
29 NullIntValue: &otherInt,
30 }
31
32 ...
33}
这些变化中的许多类似于以前的IntValue
字段名称示例,但其中一些更改值得特别调用。其中一个是ObjectValue
字段,它使用了*myObject
的参考类型,告诉JSON马歇勒预期要么对myObject
值进行引用,要么对null
值进行引用。这就是你如何定义一个具有多层定制对象深度的JSON对象。如果你的JSON数据要求它,你也可以在myObject
类型中引用另一个struct
类型,等等。
在上面的代码中要查看的另一对字段是NullStringValue
和NullIntValue
。 与StringValue
和IntValue
不同,这些值类型是参考类型*string
和*int
。 默认情况下,string
和int
类型不能有null
值,因为它们的空
值是"
和0
。 因此,如果您想要代表一个可以是单个类型或null
的字段,则需要将其作为参考。
此代码还更新了NullIntValue
字段,将值分配为4321
,以显示您如何将值分配给一个参考类型,例如*int
。在Go中,您只能使用变量创建对int
和string
等原始类型的引用,因此,为了将值分配给NullIntValue
字段,您首先将该值分配给另一个变量,即otherInt
,然后使用&otherInt
(而不是直接做&4321
)来引用该变量。
一旦您保存了更新,请使用去运行
来运行您的程序:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json data: {"intValue":1234,"boolValue":true,"stringValue":"hello!","dateValue":"2022-03-02T09:10:00Z","objectValue":{"arrayValue":[1,2,3,4]},"nullStringValue":null,"nullIntValue":4321}
您将看到此输出与您使用map[string] interface{}
值相同,但这次nullIntValue
的值为4321
,因为它是其他Int
的值。
起初,设置结构
值可能需要一些额外的时间,但一旦定义了它们,您可以在代码中反复使用它们,结果将是相同的,无论您在哪里使用它们。
Go’s JSON Marshaller 还允许您根据该值是否为空,来控制一个字段是否应包含在 JSON 输出中。有时,您可能有一个大型 JSON 对象或可选的字段,您不希望随时被包含,所以忽略这些字段可以是有用的。
现在,更新你的程序,使NullStringValue
字段omitempty
,并添加一个名为EmptyString
的新字段,具有相同的选项:
1[label main.go]
2...
3
4type myJSON struct {
5 ...
6
7 NullStringValue *string `json:"nullStringValue,omitempty"`
8 NullIntValue *int `json:"nullIntValue"`
9 EmptyString string `json:"emptyString,omitempty"`
10}
11
12...
现在,当myJSON
被调用时,如果它们的值是空的,则将从输出中排除EmptyString
和NullStringValue
字段。
保存更改后,使用去运行
来运行您的程序:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json data: {"intValue":1234,"boolValue":true,"stringValue":"hello!","dateValue":"2022-03-02T09:10:00Z","objectValue":{"arrayValue":[1,2,3,4]},"nullIntValue":4321}
此时在输出中,你会看到nullStringValue
字段不再显示。由于它被认为是空的,因为它具有null
值,所以omitempty
选项将其排除在输出中。
在本节中,您更新了您的程序以使用结构
类型来生成 JSON 数据,使用json.Marshal
而不是地图
类型。
然而,为了让您的程序融入JSON生态系统,您需要做的不仅仅是生成JSON数据,您还需要能够读取被发送的JSON数据以响应您的请求,或其他系统向您发送请求。
JSON 使用地图
与本教程的第一个部分类似,您将使用map[string] interface{}
作为生成 JSON 数据的灵活方式,您还可以使用它作为阅读 JSON 数据的灵活方式。 json.Unmarshal
函数,本质上与json.Marshal
函数相反,会将 JSON 数据转换回 Go 数据。您将提供json.Unmarshal
与 JSON 数据以及 Go 变量,将未编辑的数据放入其中,如果无法做到这一点,它将返回一个错误
值,或者如果成功了,将更新到nile
错误值。
现在,更新您的程序以使用json.Unmarshal
将 JSON 数据解析到map[string] interface{}
。你将开始用包含 JSON 字符串的jsonData
变量来替换原始的data
变量,然后你将宣布新的data
变量作为map[string] interface{}
来接收 JSON 数据,最后,你将使用json.Unmarshal
与这些变量来访问 JSON 数据。
打开main.go
文件,并用以下字符代替main
函数中的行:
1[label main.go]
2...
3
4func main() {
5 jsonData := `
6 {
7 "intValue":1234,
8 "boolValue":true,
9 "stringValue":"hello!",
10 "dateValue":"2022-03-02T09:10:00Z",
11 "objectValue":{
12 "arrayValue":[1,2,3,4]
13 },
14 "nullStringValue":null,
15 "nullIntValue":null
16 }
17 `
18
19 var data map[string]interface{}
20 err := json.Unmarshal([]byte(jsonData), &data)
21 if err != nil {
22 fmt.Printf("could not unmarshal json: %s\n", err)
23 return
24 }
25
26 fmt.Printf("json map: %v\n", data)
27}
在此更新中,将jsonData
变量设置为使用 raw string literal以允许声明覆盖多个行以便更容易阅读。
jsonData
变量被转换为json.Unmarshal
作为一个[]byte
,因为该函数需要一个[]byte
类型,而jsonData
最初被定义为一个字符串
类型,这是因为Go中的字符串
可以转换为[]byte
,反之亦然。
最后,一旦 JSON 数据被解析成数据
变量,您可以使用fmt.Printf
将其打印到屏幕上。
要运行您的更新程序,保存您的更改,并使用运行
来运行该程序:
1go run main.go
结果将看起来像这样:
1[secondary_label Output]
2json map: map[boolValue:true dateValue:2022-03-02T09:10:00Z intValue:1234 nullIntValue:<nil> nullStringValue:<nil> objectValue:map[arrayValue:[1 2 3 4]] stringValue:hello!]
这一次,你的输出显示了JSON翻译的Go侧。你有一个地图
值,包括来自JSON数据的各种字段。
现在,因为您的 Go 数据位于map[string] interface{}
,需要使用数据做一些工作,您需要使用所需的string
键值从map
中获取值,然后您需要确保您收到的值是您期望的值,因为它作为interface{}
值返回给您。
要做到这一点,打开main.go
文件,并更新您的程序,以便使用以下代码读取dateValue
字段:
1[label main.go]
2...
3
4func main() {
5 ...
6
7 fmt.Printf("json map: %v\n", data)
8
9 rawDateValue, ok := data["dateValue"]
10 if !ok {
11 fmt.Printf("dateValue does not exist\n")
12 return
13 }
14 dateValue, ok := rawDateValue.(string)
15 if !ok {
16 fmt.Printf("dateValue is not a string\n")
17 return
18 }
19 fmt.Printf("date value: %s\n", dateValue)
20}
在此更新中,您使用data[
dateValue]
将rawDateValue
作为界面{}
类型,并使用OK
变量确保dateValue
字段位于地图
中。
然后,您使用 类型声明来声称 rawDateValue' 类型实际上是一个
字符串' 值,然后将其分配给变量 `dateValue'。
最后,您可以使用「fmt.Printf」来打印「dateValue」。
若要再次运行更新后的程序,请保存您的更改并使用运行
来运行它:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json map: map[boolValue:true dateValue:2022-03-02T09:10:00Z intValue:1234 nullIntValue:<nil> nullStringValue:<nil> objectValue:map[arrayValue:[1 2 3 4]] stringValue:hello!]
3date value: 2022-03-02T09:10:00Z
您可以看到日期值
行,显示从地图
中提取的dateValue
字段,并转换为字符串
值。
在本节中,您更新了您的程序,以使用json.Unmarshal
函数与map[string] interface{}
变量,以将 JSON 数据解析为 Go 数据。
然而,这项更新确实显示了使用map[string] interface{}
在 Go 中解析 JSON 的缺点之一,因为Go 不知道每个字段的数据类型是什么(它知道的唯一事情是界面{}
),它可以做的最好的事情是解析数据是做出最好的猜测。这意味着在dateValue
字段中的time.Time
等复杂值不能为您解析,并且只能作为string
访问。如果您试图以这种方式访问map
中的任何数字值,就会出现类似的问题。
虽然使用地图
来解码 JSON 数据可以是灵活的,但在解读你所拥有的数据时,它也会为你留下更多的工作。类似于json.Marshal
函数如何使用struct
值来生成 JSON 数据,json.Unmarshal
函数可以使用struct
值来读取 JSON 数据。
JSON 使用结构
当您阅读 JSON 数据时,很可能您已经知道所接收的数据的结构;否则,这将是很难解释的。
在以前的部分中,您定义了myJSON
和myObject
的结构
值,并添加了json
结构标签,以便让Go知道在生成JSON时如何命名字段。现在您可以使用相同的结构
值来解码您所使用的JSON字符串,这可能有益于减少程序中的重复代码,如果您正在编辑和删除相同的JSON数据。 使用结构
来解析JSON数据的另一个好处是您可以告诉Go每个字段的预期数据类型。
现在,打开您的main.go
文件,更新data
变量声明以使用myJSON``结构
的引用,并添加几个fmt.Printf
行以显示myJSON
上的各种字段的数据:
1[label main.go]
2...
3
4func main() {
5 ...
6
7 var data *myJSON
8 err := json.Unmarshal([]byte(jsonData), &data)
9 if err != nil {
10 fmt.Printf("could not unmarshal json: %s\n", err)
11 return
12 }
13
14 fmt.Printf("json struct: %#v\n", data)
15 fmt.Printf("dateValue: %#v\n", data.DateValue)
16 fmt.Printf("objectValue: %#v\n", data.ObjectValue)
17}
由于您之前已经定义了结构
类型,所以您只需要更新数据
字段的类型,以支持结构
的解散。
现在,保存您的更新并使用去运行
来运行您的程序:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json struct: &main.myJSON{IntValue:1234, BoolValue:true, StringValue:"hello!", DateValue:time.Date(2022, time.March, 2, 9, 10, 0, 0, time.UTC), ObjectValue:(*main.myObject)(0x1400011c180), NullStringValue:(*string)(nil), NullIntValue:(*int)(nil), EmptyString:""}
3dateValue: time.Date(2022, time.March, 2, 9, 10, 0, 0, time.UTC)
4objectValue: &main.myObject{ArrayValue:[]int{1, 2, 3, 4}}
你会看到在json struct
行和dateValue
行,你的JSON数据中的日期值现在已经转换为time.Time
值(time.Date
格式是当%#v
被用作格式词汇时所显示的)。
另一个要注意的是,在json struct
线上出现了EmptyString
,即使它没有被包含在原始的JSON数据中。如果一个字段被包含在用于JSON解散的struct
上,并且没有被包含在JSON数据中,那一个字段就被设置为其类型的默认值,并且被忽略了。这样,你就可以安全地定义你的JSON数据可能有所有可能的字段,而不用担心如果一个字段不存在在过程的两侧。
类似于你的struct
上的EmptyString
字段被json.Unmarshal
忽略了,当emptyString
字段从JSON数据中缺少时,相反的情况也是如此。如果一个字段包含在JSON数据中,但在Gostruct
上没有相应的字段,那么这个JSON字段被忽略,并继续对接下来的JSON字段进行解析。这样,如果你正在阅读的JSON数据非常大,而你的程序只关心这些字段的少数,你可以选择创建一个struct
,其中只包含你关心的字段。在struct
上没有定义的JSON数据中的任何字段都被忽略,而Go的JSON解析器将继续在下一个字段。
要在行动中看到这一点,最后一次打开你的main.go
文件,并更新jsonData
,以包含在myJSON
中未包含的字段:
1[label main.go]
2...
3
4func main() {
5 jsonData := `
6 {
7 "intValue":1234,
8 "boolValue":true,
9 "stringValue":"hello!",
10 "dateValue":"2022-03-02T09:10:00Z",
11 "objectValue":{
12 "arrayValue":[1,2,3,4]
13 },
14 "nullStringValue":null,
15 "nullIntValue":null,
16 "extraValue":4321
17 }
18 `
19
20 ...
21}
一旦你添加了 JSON 数据,保存你的文件并使用 go run
运行它:
1go run main.go
你的输出将看起来像这样:
1[secondary_label Output]
2json struct: &main.myJSON{IntValue:1234, BoolValue:true, StringValue:"hello!", DateValue:time.Date(2022, time.March, 2, 9, 10, 0, 0, time.UTC), ObjectValue:(*main.myObject)(0x14000126180), NullStringValue:(*string)(nil), NullIntValue:(*int)(nil), EmptyString:""}
3dateValue: time.Date(2022, time.March, 2, 9, 10, 0, 0, time.UTC)
4objectValue: &main.myObject{ArrayValue:[]int{1, 2, 3, 4}}
您不应该看到此输出和以前的输出之间的任何差异,因为Go 将忽略 JSON 数据中的额外值
字段并继续。
在本节中,您更新了您的程序,以使用您之前定义的struct
类型来解析您的 JSON 数据. 您看到 Go 如何为您解析一个time.Time
值,并且忽略了在struct
类型上定义的EmptyString
字段,但不是在 JSON 数据中。
结论
在本教程中,您创建了一种新的程序,以在 Go 的标准库中使用编码/json
包。 首先,您使用了json.Marshal
函数与map[string]interface{}
类型以灵活地创建 JSON 数据。 然后,您更新了您的程序,以使用struct
类型与json
结构标签,以与json.Marshal
一贯可靠的方式生成 JSON 数据。 之后,您使用了json.Unmarshal
函数与map[string] interface{}类型来解码 JSON 字符串到数据中。 最后,您使用了您以前用
json.Unmarshal函数定义的
struct类型,让 Go 根据这些
使用编码/json
包,您将能够与互联网上许多可用的API进行交互,以创建您自己的集成与流行的网站。
除了您在本教程中使用的函数外, coding/json
包还包含其他有用的函数和类型,可用于与 JSON 交互。
本教程也是 DigitalOcean How to Code in Go系列的一部分,该系列涵盖了许多 Go 主题,从首次安装 Go 到如何使用语言本身。