七叶笔记 » golang编程 » Golang 错误处理实战

Golang 错误处理实战

go定义的error 其实是一个interface

 type error interface {
     Err or() string
}  

那么只要是实现这个接口的都可以当做一个error。譬如我们写一个除法函数:

 main. go package main

import "fmt"

func Divide(a, b int) (int, error) {
    if b == 0 {
        return 0, fmt.Errorf("can't divide '%d' by  zero ", a)
    }
    return a / b,  nil 
}  

当被除数为0 的时候则返回一个错误。

更进一步,我们可以定义一个除0的错误 ErrDivideByZero。

 package main

 import  (
    "errors"
    "fmt"
)

var ErrDivideByZero = errors.New("divide by zero")

func Divide(a, b int) (int, error) {
    if b == 0 {
        return 0, ErrDivideByZero //返回错误
    }
    return a / b, nil
}

func main() {
    a, b := 10, 0
    result, err := Divide(a, b)
    if  err  != nil {
        switch {//判断错误类型
        case errors.Is(err, ErrDivideByZero):
            fmt.Println("divide by zero error")
        default:
            fmt.Printf("unexpected division error: %s\n", err)
        }
        return
    }

    fmt.Printf("%d / %d = %d\n", a, b, result)
}  

我们在函数调用的地方,就可以通过 errors.Is 判断是否是 ErrDivideByZero。

我们再更进一步,error 里面还可以携带更多的数据,譬如我们定义 DivisionError 里面包含了除数、被除数以及错误信息。并且实现 Error 接口,如下:

 type DivisionError  struct  {
    IntA int
    IntB int
     Msg   string
}
func (e *DivisionError) Error() string { 
    return e.Msg
}  

后续使用的时候,我们就可以读取error里面的信息,然后进行响应处理了。

 func Divide(a, b int) (int, error) {
    if b == 0 {
        return 0, &DivisionError{
            Msg: fmt.Sprintf("cannot divide '%d' by zero", a),
            IntA: a, IntB: b,
        }
    }
    return a / b, nil
}

func main() {
    a, b := 10, 0
    result, err := Divide(a, b)
    if err != nil {
        var divErr *DivisionError
        switch {
        case errors.As(err, &divErr):
            fmt.Printf("%d / %d is not mathematically valid: %s\n",
              divErr.IntA, divErr.IntB, divErr.Error())
        default:
            fmt.Printf("unexpected division error: %s\n", err)
        }
        return
    }

    fmt.Printf("%d / %d = %d\n", a, b, result)
}  

上面判断error 类型的时候用的是 errors.Is ,这里 error 类型转化的时候用的是 errors.As 大家不要弄混了。

相关文章