Go语言上手:函数、结构体与常用基础操作|青训营

199 阅读5分钟

上回书中,我们介绍了Go语言中更多与变量等相关的基础语法知识。事实上,在实际开发中,我们不可避免的要封装一些操作来减少代码量。这时候,我们便需要用到函数结构体等内容来实现。接下来,我们将介绍函数结构体以及一些常用的数据处理操作的相关知识。

基础知识

函数(Functions)

  • 函数是Go语言的基本构建块,使用func关键字声明。
  • 函数可以有参数和返回值。以下是一个计算两个整数之和的函数示例:
    func add(a int, b int) int {
        return a + b
    }
    
  • Go语言支持多返回值,可以返回多个值。当函数的参数为相同类型时,你可以像定义变量那样,仅写一次类型声明。以下是一个返回两个整数之和和差的函数示例:
    func addAndSubtract(a, b int) (int, int) {
        return a + b, a - b
    }
    

指针(Pointers)

  • 指针是存储变量内存地址的变量。使用&操作符获取变量的地址,使用*操作符访问指针指向的值。
  • 以下是一个使用指针修改变量值的示例:
    func updateValue(ptr *int) {
        *ptr = 100
    }
    
    func main() {
        var num int = 10
        fmt.Println("Before update:", num)  // 输出:Before update: 10
        
        updateValue(&num)
        fmt.Println("After update:", num)   // 输出:After update: 100
    }
    

结构体(Structs)

  • 结构体是一种自定义的复合类型,用于组合不同类型的字段。
  • 使用type关键字定义结构体类型,并使用结构体字面量struct初始化结构体变量。
  • 以下是一个表示矩形的结构体示例:
    type Rectangle struct {
        width  float64
        height float64
    }
    
    func main() {
        rect := Rectangle{width: 10.0, height: 5.0}
        fmt.Println("Width:", rect.width)    // 输出:Width: 10
        fmt.Println("Height:", rect.height)  // 输出:Height: 5
    }
    

结构体方法(Methods)

  • 结构体可以定义方法,方法是与特定类型关联的函数。
  • 使用方法接收者来关联方法与结构体类型。
  • 以下是一个结构体方法计算矩形面积的示例:
    func (r Rectangle) calculateArea() float64 {
        return r.width * r.height
    }
    
    func main() {
        rect := Rectangle{width: 10.0, height: 5.0}
        area := rect.calculateArea()
        fmt.Println("Area:", area)  // 输出:Area: 50
    }
    

错误处理(Error Handling)

  • Go语言使用错误值来表示函数执行过程中的错误。
  • 函数可以返回一个错误值作为额外的返回值,通常是error类型。
  • 使用if err != nil语句来检查错误是否发生,并进行相应的处理。
  • 以下是一个读取文件内容的函数示例,返回文件内容和可能发生的错误:
    func readFile(filename string) (string, error) {
        data, err := ioutil.ReadFile(filename)
        if err != nil {
            return "", err
        }
        return string(data), nil
    }
    
    func main() {
        content, err := readFile("example.txt")
        if err != nil {
            fmt.Println("Error:", err)
            return
        }
        fmt.Println("Content:", content)
    }
    

注意,Go语言在这些方面与其他语言有一些不同之处

  • Go语言的函数支持多返回值,这在某些情况下可以简化代码。
  • Go语言的指针操作相对较少,不支持指针运算,这有助于减少指针相关的错误。
  • Go语言的结构体方法是显式声明的,而不是隐式的。这使得方法的调用更加明确和可见。
  • Go语言通过错误值来处理错误,而不是使用异常机制(如try-catch)。这种方式更加简洁和可控。

常用的数据处理操作

字符串操作

  • Go语言提供了丰富的字符串操作函数和方法,如字符串长度、拼接、切片、替换等。
  • 以下是一些常用的字符串操作示例:
    str := "Hello, World!"
    length := len(str)                        // 获取字符串长度
    substr := str[7:12]                        // 字符串切片操作
    newStr := strings.Replace(str, "Hello", "Hi", 1)  // 字符串替换
    

字符串格式化

  • Go语言使用fmt包提供了字符串格式化功能,可以根据需要将变量格式化为字符串。
  • 以下是一些常用的字符串格式化示例:
    num := 42
    str := "Hello"
    formatted := fmt.Sprintf("%s, the answer is %d", str, num)  // 格式化字符串
    fmt.Println(formatted)  // 输出:Hello, the answer is 42
    

JSON处理

  • Go语言提供了标准库encoding/json来处理JSON数据的编码和解码。
  • 可以使用json.Marshal函数将Go数据结构编码为JSON格式,使用json.Unmarshal函数将JSON数据解码为Go数据结构。
  • 以下是一个JSON编码和解码的示例:
    type Person struct {
        Name string `json:"name"`
        Age  int    `json:"age"`
    }
    
    func main() {
        p := Person{Name: "Alice", Age: 30}
        
        // JSON编码
        data, err := json.Marshal(p)
        if err != nil {
            fmt.Println("JSON encoding error:", err)
            return
        }
        fmt.Println(string(data))  // 输出:{"name":"Alice","age":30}
        
        // JSON解码
        var decoded Person
        err = json.Unmarshal(data, &decoded)
        if err != nil {
            fmt.Println("JSON decoding error:", err)
            return
        }
        fmt.Println(decoded)  // 输出:{Alice 30}
    }
    

时间处理

  • Go语言提供了time包来处理时间和日期。
  • 可以使用time.Now函数获取当前时间,使用time.Parse函数解析时间字符串,使用time.Format函数格式化时间。
  • 以下是一些常用的时间处理示例:
    now := time.Now()  // 获取当前时间
    fmt.Println(now)  // 输出:2023-07-26 14:37:37.123456789 +0000 UTC
    
    layout := "2006-01-02"
    str := "2023-07-26"
    parsed, err := time.Parse(layout, str)  // 解析时间字符串
    if err != nil {
        fmt.Println("Time parsing error:", err)
        return
    }
    fmt.Println(parsed)  // 输出:2023-07-26 00:00:00 +0000 UTC
    
    formatted := parsed.Format(layout)  // 格式化时间
    fmt.Println(formatted)  // 输出:2023-07-26
    

数字解析

  • Go语言提供了strconv包来进行字符串和数字之间的转换。
  • 可以使用strconv.Atoi函数将字符串转换为整数,使用strconv.ParseFloat函数将字符串转换为浮点数。
  • 以下是一些常用的数字解析示例:
    numStr := "42"
    num, err := strconv.Atoi(numStr)  // 字符串转整数
    if err != nil {
        fmt.Println("Number parsing error:", err)
        return
    }
    fmt.Println(num)  // 输出:42
    
    floatStr := "3.14"
    floatValue, err := strconv.ParseFloat(floatStr, 64)  // 字符串转浮点数
    if err != nil {
        fmt.Println("Float parsing error:", err)
        return
    }
    fmt.Println(floatValue)  // 输出:3.14
    

访问系统信息

  • Go语言提供了os包来获取命令行参数,查询系统变量,运行指令等。
  • 以下是一些常用的示例:
    pid := os.Getpid()  // 获取当前进程ID
    fmt.Println("Process ID:", pid)
    
    fmt.Println(os.Getenv("PATH")) // /usr/local/go/bin...
    fmt.Println(os.Setenv("AA", "BB")) // 设置环境变量
    
    buf, err := exec.Command("grep", "127.0.0.1", "/etc/hosts").CombinedOutput() //运行指令
    if err != nil {
        panic(err)
    }
    fmt.Println(string(buf)) // 127.0.0.1       localhost
    
    args := os.Args  // 获取命令行参数
    fmt.Println("Command-line arguments:", args)
    

本回书我们介绍了Go语言中与函数等有关的知识,以及一些常用的数据处理操作。欲学习更多知识,且听下回分解。

下回预告:运用基础知识进行的简单的实战案例。提示:建议提前预习计算机网络相关的知识,避免在学习实战案例时遇到障碍!