首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

Go语言处理Yaml配置文件实战

环境搭建

创建D:/zdpgo目录,将zdpgo_yaml解压到这个目录。

创建D:/zdpgo/demo目录。

初始化模块:

go mod init demo

使用vscode打开。

code .

修改 go.mod

module demo

go 1.22

require zdpgo_yaml v0.1.0

replace zdpgo_yaml v0.1.0 => ../zdpgo_yaml

写入yaml文件

编写一个Go程序,将以下数据写入到config.yaml文件中。

data := map[string]interface{} {

"name": "源滚滚编程",

"age": 33,

"email": "ygg@example.com"

}

期望的输出结果:

name: 源滚滚编程

age: 33

email: ygg@example.com

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

func main() {

data := map[string]interface{}{

"name":  "源滚滚编程",

"age":   33,

"email": "ygg@example.com",

}

// 转换为yaml

yamlData, err := yaml.Marshal(data)

if err != nil {

fmt.Println("转换为yaml失败:", err)

return

}

// 写入文件

err = os.WriteFile("config.yaml", yamlData, 0644)

if err != nil {

fmt.Println("写入yaml文件失败:", err)

return

}

// 成功

fmt.Println("写入yaml文件成功")

}

代码分析:

数据准备,使用map[string]interface{}这种数据结构准备yaml数据,这种方式简单灵活。

序列化,使用yaml.Marshal方法将Go语言的数据结构转换为yaml文件格式的字节切片。

写入文件,使用os.WriteFile将yaml数据写入到文件,0644是文件的全新,表示所有者可读,可写,其他用户可读。

错误处理,无论是在转换的时候,还是写入的时候,我们都加入了错误处理的代码,让程序更加的健壮。

写入嵌套的yaml

核心代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

func main() {

data := map[string]interface{}{

"server": map[string]interface{}{ // 服务器配置

 "host":    "127.0.0.1", // 主机地址

 "port":    8080,        // 端口号

 "timeout": "30s",       // 超时时间

},

"database": map[string]interface{}{ // 数据库配置

 "host":     "127.0.0.1",

 "port":     3306,

 "username": "root",

 "password": "root",

 "database": "zdpgo_yaml",

},

}

// 转换为yaml

yamlData, err := yaml.Marshal(data)

if err != nil {

fmt.Println("转换为yaml格式失败:", err)

return

}

// 写入到文件

err = os.WriteFile("config.yaml", yamlData, 0644)

if err != nil {

fmt.Println("写入到yaml文件失败:", err)

return

}

// 成功

fmt.Println("写入到yaml文件成功!")

}

输出结果:

database:

  database: zdpgo_yaml

  host: 127.0.0.1

  password: root

  port: 3306

  username: root

server:

  host: 127.0.0.1

  port: 8080

  timeout: 30s

读取yaml文件

假设我们有config.yaml文件如下:

name: 源滚滚编程

age: 33

使用Go语言读取这个yaml配置文件并输出所有的值。

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

type Config struct {

Name string `yaml:"name"`

Age  int    `yaml:"age"`

}

func main() {

// 读取文件

// os.ReadFile 不会打开文件句柄,可以不用使用 Close 关闭

yamlFile, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml文件失败:", err)

return

}

// 解析

var config Config

err = yaml.Unmarshal(yamlFile, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 成功了

fmt.Println(config.Name)

fmt.Println(config.Age)

}

修改yaml文件

假设我们有config.yaml文件如下:

name: 源滚滚编程

age: 33

使用Go语言解析这个配置文件,并将name修改为“张大鹏”。

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

type Config struct {

Name string `yaml:"name"`

Age  int    `yaml:"age"`

}

func main() {

// 读取

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml失败:", err)

return

}

// 解析

var config Config

err = yaml.Unmarshal(yamlData, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 解析成功

fmt.Println("解析成功:", config.Name, config.Age)

// 修改

config.Name = "张大鹏"

// 转换为yaml

newData, err := yaml.Marshal(&config)

if err != nil {

fmt.Println("转换yaml失败:", err)

return

}

// 保存

err = os.WriteFile("config.yaml", newData, 0644)

if err != nil {

fmt.Println("保存yaml失败:", err)

return

}

// 成功

fmt.Println("保存yaml成功!")

}

解析嵌套的yaml

假设有config.yaml配置文件如下:

app:

  name: "MyApp"

  version: "1.0.0"

server:

  host: "localhost"

  port: 8080

database:

  enabled: true

  connection:

      host: "localhost"

      port: 3306

      username: "root"

      password: "root"

      db: "test"

使用Go语言解析这个yaml文件,并输出数据库的IP地址是多少,以及服务端端口号是多少?

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

type Config struct {

App      ConfigApp      `yaml:"app"`

Server   ConfigServer   `yaml:"server"`

Database ConfigDatabase `yaml:"database"`

}

type ConfigApp struct {

Name    string `yaml:"name"`

Vresion string `yaml:"version"`

}

type ConfigServer struct {

Host string `yaml:"host"`

Port int    `yaml:"port"`

}

type ConfigDatabase struct {

Enabled    bool                     `yaml:"enabled"`

Connection ConfigDatabaseConnection `yaml:"connection"`

}

type ConfigDatabaseConnection struct {

Host     string `yaml:"host"`

Port     int    `yaml:"port"`

Username string `yaml:"username"`

Password string `yaml:"password"`

DB       string `yaml:"db"`

}

func main() {

// 读取文件

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml失败:", err)

return

}

// 解析

var config Config

err = yaml.Unmarshal(yamlData, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 成功

fmt.Println("数据库的IP地址", config.Database.Connection.Host)

fmt.Println("服务端端口号", config.Server.Host)

}

修改嵌套的yaml

假设有一个config.yaml配置文件,内容如下:

app:

  name: "MyApp"

  version: "1.0.0"

server:

  host: "localhost"

  port: 8080

database:

  enabled: true

  connection:

      host: "localhost"

      port: 3306

      username: "root"

      password: "root"

      db: "test"

把 server.port 改为 8888,把 database.connection.host 改成 192.168.33.33。

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

type Config struct {

App      ConfigApp      `yaml:"app"`

Server   ConfigServer   `yaml:"server"`

Database ConfigDatabase `yaml:"database"`

}

type ConfigApp struct {

Name    string `yaml:"name"`

Version string `yaml:"version"`

}

type ConfigServer struct {

Host string `yaml:"host"`

Port int    `yaml:"port"`

}

type ConfigDatabase struct {

Enabled    bool                     `yaml:"enabled"`

Connection ConfigDatabaseConnection `yaml:"connection"`

}

type ConfigDatabaseConnection struct {

Host     string `yaml:"host"`

Port     int    `yaml:"port"`

Username string `yaml:"username"`

Password string `yaml:"password"`

DB       string `yaml:"db"`

}

func main() {

// 读取yaml

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml失败:", err)

return

}

// 解析yaml

var config Config

err = yaml.Unmarshal(yamlData, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 修改yaml

// 把 server.port 改为 8888

config.Server.Port = 8888

// 把 database.connection.host 改成 192.168.33.33。

config.Database.Connection.Host = "192.168.33.33"

// 保存yaml

newData, err := yaml.Marshal(&config)

if err != nil {

fmt.Println("转换yaml失败:", err)

return

}

err = os.WriteFile("config.yaml", newData, 0644)

if err != nil {

fmt.Println("保存yaml失败:", err)

return

}

// 成功

fmt.Println("保存yaml成功!")

}

解析数组

假设有config.yaml文件,内容如下:

name: 源滚滚编程

age: 33

hobbies:

  - 篮球

  - 足球

  - 羽毛球

  - 乒乓球

使用Go语言解析这个yaml配置文件,并输出有哪些兴趣爱好。

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

type Config struct {

Name    string   `yaml:"name"`

Age     int      `yaml:"age"`

Hobbies []string `yaml:"hobbies"`

}

func main() {

// 读取

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml失败:", err)

return

}

// 解析

var config Config

err = yaml.Unmarshal(yamlData, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 输出

fmt.Println(config.Hobbies)

}

提取特定字段

假设有一个config.yaml配置文件,内容如下:

name: 源滚滚编程

age: 33

contact:

  email: "ygg@example.com"

  phone: "18811112222"

address:

  province: "重庆市"

  city: "重庆市"

使用go语言,解析这个yaml文件,提取出用户名的电话和所处城市。

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

type Config struct {

Name    string        `yaml:"name"`

Age     int           `yaml:"age"`

Contact ConfigContact `yaml:"contact"`

Address ConfigAddress `yaml:"address"`

}

type ConfigContact struct {

Email string `yaml:"email"`

Phone string `yaml:"phone"`

}

type ConfigAddress struct {

Province string `yaml:"province"`

City     string `yaml:"city"`

}

func main() {

// 读取文件

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml失败:", err)

return

}

// 解析

var config Config

err = yaml.Unmarshal(yamlData, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 提取:手机号,城市

fmt.Println("手机号:", config.Contact.Phone)

fmt.Println("城市:", config.Address.City)

}

练习1

假设有一个config.yaml文件,内容如下:

menu:

- name: "宫保鸡丁"

  type: "主菜"

  price: 38

  flavors: ["辣", "咸"]

- name: "清蒸鲈鱼"

  type: "主菜"

  price: 58

  flavors: ["鲜", "清淡"]

- name: "扬州炒饭"

  type: "主食"

  price: 22

  flavors: ["香", "甜"]

- name: "麻婆豆腐"

  type: "主菜"

  price: 28

  flavors: ["辣", "麻"]

请编写一个Go程序,完成以下任务:

读取并解析config.yaml文件

提取并打印所有主菜的名称和价格

提取并打印所有包含“辣”口味的菜的名称

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

// 菜单

type Menu struct {

Dishes []Dish `yaml:"menu"`

}

// 菜品

type Dish struct {

Name    string   `yaml:"name"`    // 菜名

Type    string   `yaml:"type"`    // 类型

Price   int      `yaml:"price"`   // 价格

Flavors []string `yaml:"flavors"` // 口味

}

func main() {

// 读取

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml失败:", err)

return

}

// 解析

var menu Menu

err = yaml.Unmarshal(yamlData, &menu)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 提取并打印所有主菜的名称和价格

fmt.Println("所有主菜的名称和价格")

for _, dish := range menu.Dishes {

if dish.Type == "主菜" {

 fmt.Printf("名称:%s,价格:%d元\n", dish.Name, dish.Price)

}

}

// 提取并打印所有包含“辣”口味的菜的名称

fmt.Println("所有包含“辣”口味的菜的名称")

for _, dish := range menu.Dishes {

for _, flavor := range dish.Flavors {

 if flavor == "辣" {

  fmt.Println(dish.Name)

  break

 }

}

}

}

练习2

department:

name: "研发部"

manager: "张三"

employees:

  - name: "李四"

    position: "高级工程师"

    age: 32

    skills:

      - "Go"

      - "Python"

      - "Docker"

  - name: "王五"

    position: "初级工程师"

    age: 25

    skills:

      - "Go"

      - "JavaScript"

  - name: "赵六"

    position: "测试工程师"

    age: 28

    skills:

      - "自动化测试"

      - "性能测试"

请编写一个Go程序,完成以下任务:

读取并解析config.yaml文件

打印部门名称和经理的姓名

找出掌握“Go”技能的员工的姓名和职位

计算部门员工的平均年龄

示例代码:

package main

import (

"fmt"

"os"

yaml "zdpgo_yaml"

)

// 配置信息

type Config struct {

Department ConfigDepartment `yaml:"department"`

}

// 部门信息

type ConfigDepartment struct {

Name      string     `yaml:"name"`    // 部门名

Manager   string     `yaml:"manager"` // 负责人

Employees []Employee `yaml:"employees"`

}

// 员工信息

type Employee struct {

Name     string   `yaml:"name"`     // 姓名

Position string   `yaml:"position"` // 职位

Age      int      `yaml:"age"`      // 年龄

Skills   []string `yaml:"skills"`   // 技能

}

func main() {

// 读取

yamlData, err := os.ReadFile("config.yaml")

if err != nil {

fmt.Println("读取yaml文件失败:", err)

return

}

// 解析

var config Config

err = yaml.Unmarshal(yamlData, &config)

if err != nil {

fmt.Println("解析yaml失败:", err)

return

}

// 打印部门名称和经理的姓名

fmt.Printf("部门名称:%s,经理姓名:%s\n", config.Department.Name, config.Department.Manager)

// 找出掌握“Go”技能的员工的姓名和职位

fmt.Println("掌握Go技能的有:")

for _, employee := range config.Department.Employees {

for _, skill := range employee.Skills {

 if skill == "Go" {

  fmt.Println(employee.Name, employee.Position)

  break

 }

}

}

// 计算部门员工的平均年龄

avgAge := 0

sumAge := 0

employeeLength := 0

for _, employee := range config.Department.Employees {

sumAge += employee.Age

employeeLength++

}

avgAge = sumAge / employeeLength

fmt.Println("平均年龄:", avgAge)

}

  • 发表于:
  • 原文链接https://page.om.qq.com/page/OFs1PHBTpGQ_mIB_QW6jzOKA0
  • 腾讯「腾讯云开发者社区」是腾讯内容开放平台帐号(企鹅号)传播渠道之一,根据《腾讯内容开放平台服务协议》转载发布内容。
  • 如有侵权,请联系 cloudcommunity@tencent.com 删除。

扫码

添加站长 进交流群

领取专属 10元无门槛券

私享最新 技术干货

扫码加入开发者社群
领券