您的位置:首页 > 教程 > 服务端类 > Golang > Go语言error的设计理念及背景演化详解

Go语言error的设计理念及背景演化详解

2022-12-07 10:39:21 来源:易采站长站 作者:

Go语言error的设计理念及背景演化详解

目录背景各语言中Error的演化C语言C++Go中Error的理念1.区分Error和Exception2.Error是一个接口总结背景作为一门相对新兴的语言,Go可以说是站在巨人...

目录
背景
各语言中 Error 的演化
C语言
C++
Go 中 Error 的理念
1. 区分 Error 和 Exception
2.Error是一个接口
总结

背景

作为一门相对新兴的语言,Go 可以说是站在巨人的肩膀上。从 Go 语法上,我们可以看出设计者对其有许多严肃的思考。其中 Error 的处理就是极具标志性的一项。

值得注意的是,Go 中的 Error 一直是一个有争议的内容。很多议案不断的提出又推翻,即便是官方的 error 库也在多个版本中不断迭代。本文内容基于 1.19.3 版本的 Go 编写。

各语言中 Error 的演化

想要了解 Error 在 Go 中占据话题的原因,我们需要先了解 Error 在编程语言中的演化。

C语言

C语言中开发者需要根据函数的返回值作错误判断。每个函数是单返回值,一般通过传递指针作为入参。返回值为 int 类型,表示成功或失败。

显然在这个阶段,语言设计者只单纯地把错误考虑为“异常”情况,由开发者判断函数的执行结果。这种情况下,错误中并没有太多信息。这会加重开发者对错误的处理工作。

C++

进入C++时代以后,语言带来了 exception 。错误会作为一个程序正常执行以外的一个特殊情况被抛出。而开发者可以通过 try....catch.... 对异常作特殊处理。

这种设计模式的影响很广,包括 Javascript 在内很多语言都延续了这种设计。其特点为,开发者可以知道错误在哪里抛出,但不能具体知道调用方会抛出什么异常。

Go 中 Error 的理念

在 Go 的 Error 中,我们可以看到两个 ERROR 的特点。

1. 区分 Error 和 Exception

第一点是,Go 中真正从语言设计上区分开了 Error 和 Exception。Go 的处理异常逻辑不引入 exception ,支持多参数返回,所以开发者可以很容易在函数签名中带上实现了 error interface 的对象,交由调用者处理。

通常如果一个函数返回了 value 和 error , 开发者需要先判定 error,再利用处理 value 处理下一步逻辑。常见代码如下:

value, err := getSomething()
if err != nil{
    // 处理错误
    return
}
// 逻辑处理

另外,Go 中引入了 panic 机制,它与其他语言的 exception 不完全一样。在其他语言中,当程序抛出异常时,相当于把 exception 抛给开发者处理。而 Go 中的 panic 是专门,针对真正意外,不可恢复的情况,如索引越界、不可恢复的环境问题、栈溢出。

同时,GO 也提供了从 panic 中恢复的接口—— recover 。但这不意味着开发者应该把其当作 try... catch... 使用。而是应该当作是程序崩溃后的特殊处理的最后机会。在 Go 的设计中,panic 一旦触发,说明程序应该要退出了。但在某些业务场景下,我们可能还会有日志上报,日志打印,信息通知等操作。此时,就应该考虑使用 recover。

2.Error是一个接口

第二点是,Error 在 Go 中其实是一个普通的接口。它不仅保存着错误的信息,还提供了一系列的方式供开发者使用。因此开发者可以自行拓展,嵌套,封装新的 error ,为项目提供自定义错误模块。

由此看来,Error 在 Go 中并不像其他语言一样,是一个特殊的类型。它只是一个普通的值,开发者完全可以自己实现一套新的 Error 接口。但更多时候,官方的 errors 库已经可以覆盖绝大多数场景了。

因此, Go 的设计并不是在定义一套新的 Error 机制。而是在制定一套 Error 在代码逻辑中处理的规范。你不必完全遵守这套规范,但在各种实际开发经验总结来看,Go 的这种设计模式确实赢得了很多开发者的青睐。

示例代码:

// 创建一个error
newErr := errors.New("一个错误")
// 判断error类型
if errors.Is(newErr, fs.ErrNotExist) {
fmt.Println("file does not exist")
} else {
fmt.Println(err)
}

总结

Go 之所以从诞生至今,吸引了这么多的粉丝。处理语言的机制以外,更多的就是它的设计理念。而本文讲述的 error 就是其中一部分。我们在使编程用 Go 开发时,除了按照它推荐的规范编码至于,还应该关心、理解它的设计。只有这样,才能写出更优秀的作品。

进一步阅读 官方 errors 库文档地址:pkg.go.dev/errors

以上就是Go语言error的设计理念及背景演化详解的详细内容,更多关于Go error设计理念的资料请关注我们其它相关文章!

如有侵权,请发邮件到 [email protected]

相关文章

  • Go+Vue开发一个线上外卖应用的流程(用户名密码和图形验证码)

    Go+Vue开发一个线上外卖应用的流程(用户名密码和图形验证码)

    这篇文章主要介绍了Go+Vue开发一个线上外卖应用(用户名密码和图形验证码),本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下图形化验证码生成和验证功能介绍在使用用户名和密码登录功能时,需要填写验证码,验证码是以图形化的方式进行获取和展示的。验证码使用原理验证码的使用流程和原理为:在服务器端负责生成图形化验证码,并以数据流的形式供前端访问获取,同时将生成的验
    2022-06-29
  • Go 微服务开发框架DMicro设计思路详解

    Go 微服务开发框架DMicro设计思路详解

    目录背景概述架构设计理念面向接口设计会话Session消息Message协议Proto编码Codec连接Socket有机的组合插件Plugin组件未来展望背景DMicro诞生的背景,是因为我...目录背景概述架构设计理念面向接口设计会话 Session消息 Message协议 Proto编码 Codec连接 Socket有机的组合插件 Plugin组件未来展望背景DMicro 诞生的背景,是因为我
    2022-10-19
  • golang用什么开发工具?

    golang用什么开发工具?

    golang用的开发工具有:1、Go Revive,是一个Go语言的代码质量检测工具;2、Go Callvis,可以用来可视化Go程序的调用图;3、Gaia,高效,快速,轻量级,并且对开发人员友好。golang用的开发工具有:1、Go Reviverevive 是一个 Go 语言的代码质量检测工具(Linter for Go),具有快速、可配置、可扩展、灵活和美观等特性,可作为 golint 的替
    2020-08-07
  • golang是多线程模式吗?

    golang是多线程模式吗?

    golang是多线程模式的,golang的线程模型是M P G模型,整体上Go程与内核线程是多对多对应的,因此首先来讲就一定是多线程的。golang是多线程模式。 由于gmp中的p与m是将p绑定与m内核线程上,而后p的最大数量有GOPROCESS确定,而M内核线程的数量会由go去限制为10K个,但是由于内核原因做不到这么多,所以这个限制就当做没有吧。拿个图明确一下Golang有些所谓的M比N模型,
    2020-08-07
  • golang用什么开发工具?

    golang用什么开发工具?

    golang用的开发工具有:1、Go Revive,是一个Go语言的代码质量检测工具;2、Go Callvis,可以用来可视化Go程序的调用图;3、Gaia,高效,快速,轻量级,并且对开发人员友好。golang用的开发工具有:1、Go Reviverevive 是一个 Go 语言的代码质量检测工具(Linter for Go),具有快速、可配置、可扩展、灵活和美观等特性,可作为 golint 的替
    2020-08-07
  • golang是单进程的吗?

    golang是单进程的吗?

    golang不是单进程的,而是多线程;golang的线程模型是M P G模型,整体上Go程与内核线程是多对多对应的,因此首先来讲就一定是多线程的。golang不是单进程的,而是多线程。Golang有些所谓的M比N模型,M个线程下可以创建N个go routine,一般而言N远大于M,本质上属于多线程模型,但是协程的调度由Go的runtime决定,强调开发者应该使用channel进行协程之间的同步。至
    2020-08-07
  • 代码详解使用Go基于WebSocket构建视频直播弹幕系统

    代码详解使用Go基于WebSocket构建视频直播弹幕系统

    (1)业务复杂度介绍开门见山,假设一个直播间同时500W人在线,那么1秒钟1000条弹幕,那么弹幕系统的推送频率就是: 500W * 1000条/秒=50亿条/秒 ,想想B站2019跨年晚会那次弹幕系统得是多么的NB,况且一个大型网站不可能只有一个直播间!使用Go做WebSocket开发无非就是三种情况:使用Go原生自带的库,也就是 golang.org/x/net ,但是这个官方库真是出了奇Bu
    2020-08-07
  • PHP语法和Go语法有什么差异?对比介绍

    PHP语法和Go语法有什么差异?对比介绍

    本篇文章给大家对比一下PHP语法和Go语法,带大家了解一下PHP语法和Go语法之间的差异。有一定的参考价值,有需要的朋友可以参考一下,希望对大家有所帮助。Go 是由 Google 设计的一门静态类型的编译型语言。它有点类似于 C,但是它包含了更多的优点,比如垃圾回收、内存安全、结构类型和并发性。它的并发机制使多核和网络机器能够发挥最大的作用。这是 GoLang 的最佳卖点之一。此外,Go 速度快,
    2020-08-07