golang 函数式编程库samber/mo使用: Option

golang 函数式编程库samber/mo使用: Option

1. samber/mo 是什么?

samber/mo是一个Go语言库,它提供了一组函数式编程(FP)的抽象,包括Monad。这些抽象可以帮助你更好地组织和处理你的代码,尤其是在处理异步和错误处理等方面。

2. Monad是什么?

在函数式编程中,Monad就像是一个智能的盒子,它可以包装各种值,并且可以按照特定的规则将一系列的函数链接在一起。

举一个简单的例子来理解Monad。假设你正在组织一场宴会,你需要完成一系列的任务,比如购买食材,准备食物,设置餐桌,邀请客人等。我们假定每个任务都依赖于前一个任务的完成,比如你不能在购买食材之前准备食物,也不能在设置餐桌之前邀请客人。

  buyGroceries -> prepareFood -> setTable -> inviteGuests

在这个例子中,每个任务都可以看作是一个函数,每个函数的输入是前一个函数的输出。Monad就是一个可以将这些函数按照正确的顺序链接在一起的结构。在这个结构中,每个函数的输出都被包装在一个盒子(Monad)中,下一个函数可以从盒子中取出这个值,并使用它作为输入。

此外,如果在执行任务的过程中出现了错误(比如食材没有买到),Monad可以立即停止后续的任务,并返回一个表示错误的值。这就像是你在准备宴会的过程中准备食物失败(翻车),于是你决定取消宴会,而不是继续准备。

  buyGroceries -> prepareFood(failed!)

这就是Monad的基本概念。通过使用Monad,我们可以将复杂的函数序列简化为简洁的管道,抽象出控制流和副作用,使代码更加清晰和易于理解。

这个例子中的Monad可以看作是samber/mo库中的Option类型。Option类型是一种表示可能存在值的类型,它可以包装任意类型的值,并提供了一系列的操作来处理这个值。 实现如下。

package mainimport ("fmt""github.com/samber/mo"
)func buyGroceries() mo.Option[string] {// Here we simulate a successful operationreturn mo.Some("groceries")
}func prepareFood(groceries string) mo.Option[string] {// Here we simulate a failed operationreturn mo.None[string]()
}func setTable(food string) mo.Option[string] {// Here we simulate a successful operationreturn mo.Some("table set")
}func inviteGuests(table string) mo.Option[string] {// Here we simulate a successful operationreturn mo.Some("guests invited")
}func main() {groceries := buyGroceries()groceries.Match( // 如果groceries不是None,就执行第一个函数;否则执行第二个函数func(groceries string) (string, bool) {fmt.Println("groceries bought")return groceries, true},func() (string, bool) {fmt.Println("something went wrong")return "", false},).FlatMap(func(groceries string) mo.Option[string] {// 如果groceries不是None,就执行这个函数;否则返回Nonereturn prepareFood(groceries)}). FlatMap(func(food string) mo.Option[string] {return setTable(food)}).FlatMap(func(table string) mo.Option[string] {return inviteGuests(table)}).Match(func(guests string) (string, bool) {fmt.Println("everything is ready")return guests, true},func() (string, bool) {fmt.Println("something went wrong")return "", false},)
}

输出

groceries bought
something went wrong

3. Option类型构造

samber/mo库中的Option类型是一种表示可能存在值的类型。它有两种状态:Some表示有值,None表示没有值。Option类型的构造主要包括

  • Some:将一个值包装到Option中
  • None:创建一个空的Option

4. Option类型的操作

samber/mo库中的Option类型提供了一系列的操作,可以帮助我们处理可能存在值的情况。这些操作包括:

  • Match:根据Option的值执行不同的操作, 如果Option有值则执行第一个函数, 否则执行第二个函数 doc - play
  • IsPresent:判断Option是否包含值 doc - play
  • IsAbsent:判断Option是否为空 doc - play
  • Size:返回Option的大小, 如果有值则返回1, 否则返回0 doc - play
  • Get:获取Option的值 doc - play
  • MustGet:获取Option的值,如果Option为空,则panic doc - play
  • OrElse:如果Option为空,返回一个默认值 doc - play
  • OrEmpty:如果Option为空,返回一个空的Option doc - play
  • ToPointer:将Option的值转换为指针 doc - play
  • ForEach:如果Option有值,则执行一个函数 doc
  • Map:如果Option有值,则将一个函数应用到Option的值,并返回一个新的Option; 如果Option为空,则返回None doc - play
  • MapNone:如果Option为空,则将一个函数应用到Option的值,并返回一个新的Option; 如果Option有值,则返回None doc - play
  • FlatMap: 和Map类似,只是mapper函数格式不同 doc - play
  • MarshalJSON:将Option的值转换为JSON格式, 如果Option为空, 则执行json.Marshal(nil) doc
  • UnmarshalJSON:将JSON格式的值转换为Option doc
  • Scan: 实现了sql.Scanner接口,可以将数据库查询结果转换为Option doc
  • Value: 实现了driver.Valuer接口,可以将Option转换为数据库查询参数 doc

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/702580.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

力扣随笔之移除元素(简单27)

思路:定义一个指针left,使该指针及该指针左边的数全部都不等于val,定义一个遍历指针i,若nums[i] val,则i自加,若nums[i] ! val,则将left,并将nums[i]的值赋给nums[left]&#xff0c…

MySQL引擎对决:深入解析MyISAM和InnoDB的区别

欢迎来到我的博客,代码的世界里,每一行都是一个故事 MySQL引擎对决:深入解析MyISAM和InnoDB的区别 前言引擎概述MyISAM:InnoDB: 使用场景使用 MyISAM 的最佳实践:使用 InnoDB 的最佳实践:可能的…

Qt/Slot与Signal /信号与信号连接/信号与槽的关系

一个信号可以绑定多个槽 signalObject* sg1 new signalObject():slotObject* sl1 new slotObject();QPushButton* btn new QPushButton(); connect(sg1, &slotObject::signal1(), sl1, &signalObject::slot1());connect(sg1, &slotObject::signal1(), sl1, …

Jenkins自动化部署构建说明(8)

Jenkins构建说明 - 20211012 什么是Jenkins? Jenkins 是一款流行的开源持续集成(Continuous Integration)工具,广泛用于项目开发,具有自动化构建、测试和部署等功能。它是一个自动化的周期性的集成测试过程,从检出代…

QT day3 作业2.22

思维导图: 作业: 完善对话框,点击登录对话框,如果账号和密码匹配,则弹出信息对话框,给出提示”登录成功“,提供一个Ok按钮,用户点击Ok后,关闭登录界面,跳转到…

ChatGPT Plus遇到订阅被拒原因与解决方案

ChatGPT Plus被广泛认为相比普通版本更快、更强,并且能最先体验新功能。 很多小伙伴再订阅时遇到图片中的问题 错误提示包括这些: Your credit card was declined.Try paying with a debit card instead.您的信用卡被拒绝了。请尝试用借记卡支付。你的…

【Python】遇到的一些小问题及解决办法汇总

【工具】:pycharm 【环境】:Windows 一、数据集路径导入报错 【错误提示】: SyntaxError: (unicode error) ‘unicodeescape’ codec can’t decode bytes in position 2-3: truncated \UXXXXXXXX escape 如图: 【原因分析】&a…

pytest如何在类的方法之间共享变量?

在pytest中,setup_class是一个特殊的方法,它用于在类级别的测试开始之前设置一些初始化的状态。这个方法会在类中的任何测试方法执行之前只运行一次。 当你在setup_class中使用self来修改类属性时,你实际上是在修改类的一个实例属性。在Pyth…

突破编程_C++_高级教程(内存管理(2))

1 内存泄漏的预防与处理 内存泄漏是指程序中已动态分配的堆内存由于某种原因程序未释放或无法释放,造成系统内存的浪费,导致程序运行速度减慢甚至系统崩溃等严重后果。内存泄漏缺陷具有隐蔽性、积累性的特征,比其他如内存非法访问等问题更难…

数据库的介绍、分类、作用和特点

数据库是用来存储和管理数据的系统。它提供了一种结构化的方式来组织和存储数据,以便于有效地进行数据的增删改查操作。 数据库可以按照不同的分类方式进行分类,下面是一些常见的分类方式: 关系型数据库(RDBMS)&#…

嵌入式学习第二十天!(进程)

进程基本概念: 1. 进程: 程序:存放在外存中的一段数据组成的文件 进程:是一个程序动态执行的过程,包括进程的创建、进程的调度、进程的消亡 2. 进程相关命令: 1. top: 动态查看当前系统中的所有进程信息…

6.4 应用组件 Application

本节介绍Android的重要组件Application的基本概念和常见用法:首先说明Application的生命周期贯穿了App的整个运行过程,然后利用Application实现App全局变量的读写,以及如何避免方法数过多的问题,最后阐述如何借助App实例来操作Roo…

pytorch -- torch.nn.Module

基础 torch.nn 是 PyTorch 中用于构建神经网络的模块。nn.Module包含网络各层的定义及forward方法。 在用户自定义神经网络时,需要继承自nn.Module类。通过继承 nn.Module 类,您可以创建自己的神经网络模型,并定义模型的结构和操作。 torch.n…

简单学习语音唤醒

目录 一、总体介绍 二、来到讯飞开放平台 ​三、代码修改 1.ivw_sample.cpp代码修改 (1)库的导入 (2)宏定义​编辑 (3)定义 (4)修改OnOutput​编辑 (5&#xff0…

C语言——oj刷题——判断闰年

当我们谈到判断闰年时,我们通常会遵循以下规则:闰年是指能被4整除但不能被100整除的年份,或者能被400整除的年份。在C语言中,我们可以通过编写一个简单的程序来实现这一功能。下面是一个示例代码,用于判断一个给定年份…

C++多态的原理

目录 函数虚表 多态原理 普通调用和多态调用的区别 函数虚表 含有虚函数的类&#xff0c;都会有一个函数虚表指针&#xff0c;指向函数虚表。 class Base{public:virtual void Func1(){cout << "Func1()" << endl;}private:int _b 1;}; _vfptr就是函…

如何在C++中实现文件操作

大家好&#xff0c;今天给大家介绍如何在C中实现文件操作&#xff0c;文章末尾附有分享大家一个资料包&#xff0c;差不多150多G。里面学习内容、面经、项目都比较新也比较全&#xff01;可进群免费领取。 在C中&#xff0c;实现文件操作主要涉及到 <fstream> 库&#xf…

批量删除传参那些事

接口参数&#xff1a; public Object batchDeleteUsers(RequestBody List userIds) 工具提示传参&#xff1a; { “userIds”: [] } 错误&#xff01;&#xff01;&#xff01;讨逆猴子 报错&#xff1a;JSON parse error: Cannot deserialize value of type java.util.ArrayL…

Oracle PL/SQL Programming 第7章:Working with Program Data 读书笔记

总的目录和进度&#xff0c;请参见开始读 Oracle PL/SQL Programming 第6版 几乎您编写的每个 PL/SQL 块都会定义和操作程序数据。 程序数据由仅存在于 PL/SQL 会话中的数据结构组成&#xff08;物理上&#xff0c;在会话的程序全局区域或 PGA 中&#xff09;&#xff1b; 它们…

[10] v-model补充

目录 自定义组件的 v-modelv-model简化代码 自定义组件的 v-model 组件上的 v-model 默认会利用名为 value 的 prop 和名为 input 的事件。 <input v-model"parentData"> 等价于&#xff1a; <input :value"parentData"input"parentData …