全国免费咨询:

13245491521

VR图标白色 VR图标黑色
X

中高端软件定制开发服务商

与我们取得联系

13245491521     13245491521

2024-05-27_还在为 Go 中繁琐 if-else 逻辑的烦恼 那就用 vowlink 来解决

您的位置:首页 >> 新闻 >> 行业资讯

还在为 Go 中繁琐 if-else 逻辑的烦恼 那就用 vowlink 来解决 我是 LEE,老李,一个在 IT 行业摸爬滚打 17 年的技术老兵。 在开始今天的话题之前,我想先从这段代码开始今天的内容分享。在日常的开发过程中,我们经常遇到需要在业务逻辑代码中使用 if-else 语句。 然而,随着业务的增长,这种 if-else 逻辑代码往往会变得越来越复杂,逻辑判断也会变得越来越多,导致代码的可读性和可维护性下降。因此,我们需要考虑如何优化这种 if-else 逻辑代码。 举个例子,假设我们正在使用 gin 框架开发一个 web service,需要根据不同的请求参数来执行不同的逻辑来更改数据库中的数据。在这种情况下,我们通常会使用 if-else 语句来实现这个功能。 funcUpdateData(c*gin.Context){ varreqstruct{ IDint`json:"id"` Namestring`json:"name"` } //解析请求参数,将请求参数绑定到结构体中 iferr:=c.ShouldBindJSON(err!=nil{ c.JSON(http.StatusBadRequest,gin.H{"error":err.Error()}) return } //解析出的参数有效性检查,当然这里已经很多库实现了参数校验,这里只是举例 ifreq.ID==0{ c.JSON(http.StatusBadRequest,gin.H{"error":"idisrequired"}) return } ifreq.Name==""{ c.JSON(http.StatusBadRequest,gin.H{"error":"nameisrequired"}) return } //根据请求参数执行不同的逻辑,根据结果返回不同的响应 ifresult,err:=db.UpdateName(req.ID,req.Name);err!=nil{ c.JSON(http.StatusInternalServerError,gin.H{"error":err.Error()}) return }else{ c.JSON(http.StatusOK,gin.H{"message":"success","result":result}) } } 这段代码展示了在使用 gin 框架开发 Handle 时常见的逻辑。然而,随着业务的增长,其中的 if-else 逻辑代码变得越来越复杂,逻辑判断也变得越来越多,导致代码的可读性和可维护性下降。 值得注意的是,c.ShouldBindJSON(&req) 的输出作为 db.UpdateName(req.ID, req.Name) 的输入,中间经过大量的 if-else 逻辑代码进行参数校验和错误处理。我们可以整理思路,将从 req 到 c.JSON 的逻辑视为一条具有多个可控分支的路径。 另外,我们再看一个例子:这段代码展示了一个经典的嵌套 if-else 逻辑代码(地域嵌套)。如果在其中发现了无法预料的错误,将会带来很大的困扰。 funcdoSomething(dataStruct)error{ company:=data.Commpay ifcompany.Name=="hw"{ techGroup:=company.TechGroup iftechGroup.Type=="electronic"{ groupType:=techGroup.GroupType ifgroupType.Level=="A"{ groupResearch:=groupType.Research ifgroupResearch.Product=="phone"{ proVersion:=groupResearch.Version ifproVersion.Version=="1"{ //dosomething }else{ //dosomething } }else{ //dosomething } }else{ //dosomething } }else{ //dosomething } } } 在 Golang 中,由于缺乏像 try 和 catch 这样的语法结构,我们通常使用 if-else 逻辑代码来实现参数校验、错误处理和业务逻辑等多种功能。 然而,这种做法往往导致代码变得复杂,逻辑判断增多,可读性和可维护性下降。 那么,如何利用 Golang 的函数式编程来简化 if-else 逻辑代码呢?让我们开始今天的故事。 事件背景2023 年底,一位同事向我求助,他在开发业务逻辑时遇到了频繁的错误,并且花费了整个周末都无法解决问题。 我询问了他具体的情况,他说问题出现在一个复杂的 if-else 逻辑代码中,其中的逻辑判断过多,导致代码变得复杂难以理解,他不知道从何处着手进行优化。我表示愿意帮助他,并开始对代码进行审查。 经过仔细查看,我发现他的代码确实是一个典型的 if-else 逻辑代码,其中的逻辑判断过多,导致代码复杂且难以维护。我告诉他,他需要对代码进行优化。他认可这一点,但是不知道如何下手。 我们进行了一段时间的讨论,通过大量的断点调试和代码追踪,最终发现了一个逻辑判断错误,导致了后续大量嵌套的 if-else 逻辑代码无法执行。 为了解决这个问题,我决定从零开始编写一个 Golang 的通用库,用于优化复杂的 if-else 逻辑代码。 这个库将提供链式调用、处理结果前后依赖、错误处理、兜底处理以及多种调用链之间的竞争等功能,以帮助开发人员优化复杂的逻辑判断流程。 通过反复的调研发现 JavaScript 中的 Promise 对于处理这样的操作非常方便,因此我决定借鉴 Promise 的概念,实现一个类似于 Promise 的函数式编程库,用于优化复杂的 if-else 逻辑代码。 于是,vowlink 诞生了。 痛点分析如前文所述,随着业务的增长,复杂的 if-else 逻辑代码会变得越来越复杂,逻辑判断也会增多,导致代码的可读性和可维护性下降。为了解决这个问题,我们需要考虑优化这种逻辑代码的方法。 以下是需要解决的问题和痛点: 代码复杂:反复编写 if-else 逻辑代码导致代码复杂,难以理解。代码重复:逻辑判断代码重复导致代码冗余,难以维护。逻辑混乱:逻辑判断代码嵌套导致逻辑混乱,难以阅读。风险未知:逻辑判断代码存在潜在风险,导致系统不稳定,难以维护。为了解决以上问题,我们需要具备以下特点的工具: 简单易用:工具易于上手,学习成本低。高效执行:工具能够快速、高效地处理各种逻辑控制任务。逻辑控制:工具提供逻辑控制功能,简化复杂的逻辑判断。错误处理:工具提供错误处理功能,处理各种错误信息。兜底处理:工具提供兜底处理功能,处理最终的逻辑。竞争关系:工具提供处理多种调用链之间竞争关系的功能。项目介绍vowlink : https://github.com/shengyanli1982/vowlink 1111.pngvowlink 是一个基于 Golang 的函数式编程库,旨在优化复杂的 if-else 逻辑代码。它借鉴了 JavaScript 中 Promise 的概念,并提供了链式调用、处理结果前后依赖、错误处理、兜底处理以及多种调用链之间的竞争等功能。 vowlink 不是要取代 Golang 的 if-else 的写法,而是提供一种优化的选项,没有非黑即白。这里需要强调下:因为每一个开发者的习惯不同,这个库可能不适合你,但并不意味着 vowlink 不好。它是经过其他开发者的测试和试用后才开源的。 vowlink 的目标是提供一个简单易用的 Golang 库,用于优化复杂的逻辑控制流程,以提高代码的可读性和可维护性。 vowlink 提供以下功能来优化代码逻辑: 链式调用: 通过链式调用方式简化复杂的 if-else 逻辑代码。处理前后依赖: 使用 Then().Then() 方法处理结果前后依赖,上次执行结果作为下一次执行的输入。错误处理: 使用 Catch() 方法处理错误信息,提高代码的可读性。兜底处理: 使用 Finally() 方法处理最终的逻辑,如资源释放等。调用链竞争: 使用 Race()、All()、Any() 和 AllSettled() 方法处理多种调用链之间的竞争关系。在 vowlink 的世界中,每个 vow 都类似于 JavaScript 的 Promise,它可以表示异步操作的结果或状态。vow 具有三种状态:Pending、Fulfilled 和 Rejected。一旦 vow 的状态发生改变,它将保持不变,与 JavaScript 的 Promise 的状态相同。 vow 与 Race()、All()、Any() 和 AllSettled() 函数没有必然的关联,它们可以独立运行。然而,在 vowlink 中,它们是一家人,都是 vow 的一种表现形式。简单来说,Race()、All()、Any() 和 AllSettled() 函数是更高级的容器,用于处理多个 vow 之间的竞争、并行和串行操作。 基于 vow 的特性,vowlink 提供了一系列函数,使开发者能够更方便地编写逻辑判断流程。同时,结合 Race()、All()、Any() 和 AllSettled() 函数,可以处理多个调用链之间的竞争关系。在大多数情况下,vowlink 可以替代复杂的 if-else 逻辑代码,提高代码的可读性和可维护性。 尽管在 GitHub 上可以找到许多类似的库,但我发现这些库要么功能过于复杂,要么功能过于简单,要么代码过于复杂,要么代码过于简单。因此,我决定从零开始,自己动手实现一个轻量级的函数式逻辑控制库,这就是 vowlink。 设计初衷: 轻量化:vowlink 是一个精简的库,代码量少,易于使用。简单易用:vowlink 提供简洁的接口,只需几行代码即可完成任务处理逻辑编写。高效执行:vowlink 执行效率高,能够快速、高效地处理各种逻辑控制任务。状态机设计 为了让 vowlink 简单易用且高效执行,它的架构设计必须简洁可靠。 由于 vowlink 在某种程度上可以被视为 JavaScript 中 Promise 的实现,因此 vowlink 的状态机设计也参考了 JavaScript 中 Promise 的状态机设计。 Promise 流程图vow-link-1.pngPromise 状态定义PromiseState 是一个枚举类型,它定义了 Promise 的三种状态:Pending、Fulfilled 和 Rejected。 //定义 Promise 的三种状态:Pending、Fulfilled 和 Rejected //DefinethethreestatesofaPromise:Pending,Fulfilled,andRejected const( // Pending 代表一个 Promise 的 pending 状态,即 Promise 还在等待结果,既没有完成也没有被拒绝。 //Pendingrepresentsthependingstateofapromise,whichmeansthePromiseisstillwaitingfortheresult,neitherfulfillednorrejected. PendingPromiseState=iota // Fulfilled 代表一个 Promise 的 fulfilled 状态,即 Promise 已经完成,有一个确定的结果值。 //Fulfilledrepresentsthefulfilledstateofapromise,whichmeansthePromiseisfulfilledandhasadefiniteresultvalue. Fulfilled // Rejected 代表一个 Promise 的 rejected 状态,即 Promise 已经被拒绝,有一个确定的错误原因。 //Rejectedrepresentstherejectedstateofapromise,whichmeansthePromiseisrejectedandhasadefinitereasonfortheerror. Rejected ) Promise 结构体定义Promise 是一个结构体,它代表一个 Promise。内部结构也非常的简单,由状态,结果和错误信息组成。 // Promise 是一个结构体,它代表一个 Promise。Promise 是一种编程模式,用于处理异步操作。 //PromiseisastructthatrepresentsaPromise.APromiseisaprogrammingpatternforhandlingasynchronousoperations. typePromisestruct{ // state 是 Promise 的状态,它可以是 Pending、Fulfilled 或 Rejected。 //stateisthestateofthePromise,itcanbePending,Fulfilled,orRejected. statePromiseState // value 是 Promise 的值,当 Promise 被 resolve 时,这个值会被设置。 //valueisthevalueofthePromise,thisvaluewillbesetwhenthePromiseisresolved. valueinterface{} // reason 是 Promise 被拒绝的原因,当 Promise 被 reject 时,这个值会被设置。 //reasonisthereasonthePromisewasrejected,thisvaluewillbesetwhenthePromiseisrejected. reasonerror } 接口设计 vowlink 的接口设计简洁明了,通过链式调用方式将内部的多个方法串联起来,实现逻辑控制。 方法接口vowlink 提供了几个简洁易用的方法接口: Then: 用于处理成功的逻辑,类似于处理 if 逻辑代码中的 if err == nil 后的操作。Catch: 用于处理失败的逻辑,类似于处理 if 逻辑代码中的 if err != nil 后的操作。Finally: 用于处理最终的逻辑,类似于处理 if 逻辑代码中的 defer 后的操作。GetValue: 用于获取当前处理结果。GetReason: 用于获取当前处理的错误信息。在提供的接口方法中,Then、Catch、Finally 方法是执行方法,而 GetValue 和 GetReason 方法是结果方法。 GetValue 和 GetReason 方法获取的结果是在 Then、Catch、Finally 方法执行完成后的结果。 返回结果当使用 vowlink 执行一个函数的逻辑控制时,经过多次判断和处理后,最终会返回一个新的 Promise 结构体,其中包含函数的执行结果和错误信息。可以通过 GetValue 和 GetReason 方法获取结果和错误信息。 举个例子: funcmain(){ //创建一个新的Promise //CreateanewPromise result:=vl.NewPromise(func(resolvefunc(interface{},error),rejectfunc(interface{},error)){ //这个promise直接解析为"helloworld" //Thispromiseisdirectlyresolvedto"helloworld" resolve("helloworld",nil) }) //从promise中获取值并打印 //Getthevaluefromthepromiseandprintit fmt.Println(result.GetValue()) } 使用示例 以下示例展示了如何使用 vowlink 优化 if-else 逻辑代码。通过创建两个不同状态的 vow,一个成功的 vow 和一个失败的 vow,然后使用 Then 方法处理成功的逻辑,使用 Catch 方法处理失败的逻辑。 最后,使用 GetValue 和 GetReason 方法获取结果和错误信息。 更多的示例,可以参考 vowlink 项目中的 examples 目录里面的示例代码。那里面已经基本覆盖了常见的用法。 举个例子: packagemain import( "fmt" vl"github.com/shengyanli1982/vowlink" ) funcmain(){ // vowlink 像一个链条,你可以在链条上添加更多的 then()来在 promise 解析后做更多的事情。 //vowlinkislikeachain,youcanaddmorethen()tothechaintodomorethingsafterthepromiseisresolved. result:=vl.NewPromise(func(resolvefunc(interface{},error),rejectfunc(interface{},error)){ //这个promise直接解析为"helloworld" //Thispromiseisdirectlyresolvedto"helloworld" resolve("helloworld",nil) }).Then(func(valueinterface{})(interface{},error){ //在Then方法中,我们将解析的值加上"vowlink!!" //IntheThenmethod,weappend"vowlink!!"totheresolvedvalue returnvalue.(string)+"vowlink!!",nil },func(errerror)(interface{},error){ //如果promise被拒绝,我们将返回一个新的错误信息"rejected." //Ifthepromiseisrejected,wereturnanewerrormessage"rejected." returnnil,fmt.Errorf("rejected.") }) //从promise中获取值并打印 //Getthevaluefromthepromiseandprintit fmt.Println("Resolve:",result.GetValue()) //这是一个被拒绝的promise //Thisisarejectedpromise result=vl.NewPromise(func(resolvefunc(interface{},error),rejectfunc(interface{},error)){ //这个promise被拒绝,原因是"error" //Thispromiseisrejectedwiththereason"error" reject(nil,fmt.Errorf("error")) }).Then(func(valueinterface{})(interface{},error){ //如果promise被解析,我们将解析的值加上"vowlink" //Ifthepromiseisresolved,weappend"vowlink"totheresolvedvalue returnvalue.(string)+"vowlink",nil },func(errerror)(interface{},error){ //如果promise被拒绝,我们将返回一个新的错误信息"rejected." //Ifthepromiseisrejected,wereturnanewerrormessage"rejected." returnnil,fmt.Errorf("rejected.") }) //从promise中获取拒绝的原因并打印 //Getthereasonfortherejectionfromthepromiseandprintit fmt.Println("Rejected:",result.GetReason().Error()) } 输出结果: $gorundemo.go Resolve:helloworldvowlink!! Rejected:rejected. 总结vowlink 是一个轻量级的库,用于对函数进行逻辑控制。它的设计简单、易用且高效,使得开发人员能够以较低的学习成本快速上手。 通过使用 vowlink,我们能够标准化重试操作,并实现逻辑代码的多处复用。这大大减少了重复编写代码的时间,提高了开发质量。使用 vowlink,整个项目的代码看起来更加清爽、简洁而不简单。 如果您有任何问题或建议,请在 vowlink 的 GitHub 上提出 issue。我将尽快回复您的问题。 阅读原文

上一篇:2022-12-18_2022「搞笑野生动物摄影奖」公布,我的快乐和治愈回来了! 下一篇:2024-01-27_专业储存 为你保驾护航|闪迪至尊超极速SDXC UHS-II存储卡(V60)体验

TAG标签:

15
网站开发网络凭借多年的网站建设经验,坚持以“帮助中小企业实现网络营销化”为宗旨,累计为4000多家客户提供品质建站服务,得到了客户的一致好评。如果您有网站建设网站改版域名注册主机空间手机网站建设网站备案等方面的需求...
请立即点击咨询我们或拨打咨询热线:13245491521 13245491521 ,我们会详细为你一一解答你心中的疑难。
项目经理在线

相关阅读 更多>>

猜您喜欢更多>>

我们已经准备好了,你呢?
2022我们与您携手共赢,为您的企业营销保驾护航!

不达标就退款

高性价比建站

免费网站代备案

1对1原创设计服务

7×24小时售后支持

 

全国免费咨询:

13245491521

业务咨询:13245491521 / 13245491521

节假值班:13245491521()

联系地址:

Copyright © 2019-2025      ICP备案:沪ICP备19027192号-6 法律顾问:律师XXX支持

在线
客服

技术在线服务时间:9:00-20:00

在网站开发,您对接的直接是技术员,而非客服传话!

电话
咨询

13245491521
7*24小时客服热线

13245491521
项目经理手机

微信
咨询

加微信获取报价