当前位置: 首页 > news >正文

Go语言断言和类型查询

Go语言断言和类型查询

1、类型断言

类型断言(Type Assertion)是一个使用在接口值上的操作,用于检查接口类型变量所持有的值是否实现了期望的接

口或者具体的类型。

在Go语言中类型断言的语法格式如下:

// i.(TypeNname)
value, ok := x.(T)

其中,x 表示一个接口的类型,如果是具体类型变量,则编译器会报non-interface type xxx on left,T 表

示一个具体的类型(也可为接口类型)。

该断言表达式会返回 x 的值(也就是 value)和一个布尔值(也就是 ok),可根据该布尔值判断 x 是否为 T 类

型:

  • 如果 T 是具体某个类型,类型断言会检查 x 的动态类型是否等于具体类型 T。如果检查成功,类型断言返回的

    结果是 x 的动态值,其类型是 T。

  • 如果 T 是接口类型,类型断言会检查 x 的动态类型是否满足 T。如果检查成功,x 的动态值不会被提取,返回

    值是一个类型为 T 的接口值。

  • 无论 T 是什么类型,如果 x 是 nil 接口值,类型断言都会失败。

示例代码如下:

package mainimport ("fmt"
)func main() {var x interface{}x = 10value, ok := x.(int)// 10,truefmt.Print(value, ",", ok)
}

运行结果如下:

# 程序结果
10,true

需要注意如果不接收第二个参数也就是上面代码中的 ok,断言失败时会直接造成一个 panic,如果 x 为 nil 同样也

会 panic。

示例代码如下:

package mainimport ("fmt"
)func main() {var x interface{}x = "Hello"value := x.(int)fmt.Println(value)
}

运行结果如下:

# 输出结果
panic: interface conversion: interface {} is string, not int

接口断言通常可以使用 comma,ok 语句来确定接口是否绑定某个实例类型,或者判断接口绑定的实例类型是否实

现另一个接口。

re,ok := body.(io.ReadCloser)
if,ok :=  r.Body.(*maxBytesReader);

2、类型查询

接口类型查询的语法格式如下:

switch v := i.(type){case typel:XXXXcase type2:XXXXdefault:XXXX
}

接口查询有两层语义,一是查询一个接口变量底层绑定的底层变量的具体类型是什么,二是查询接口变量绑定的底

层变量是否还实现了其他接口。

(1)、i 必须是接口类型

具体类型实例的类型是静态的,在类型声明后就不再变化,所以具体类型的变量不存在类型查询,类型查询一定是

对一个接口变量进行操作。也就是说,上文中的i必须是接口变量,如果i是未初始化接口变量,则v的值是 nil。

package mainimport ("fmt""io"
)func main() {var i io.Reader//此处i是为未初始化的接口变量,所以v为nilswitch v := i.(type) {case nil://<nil>fmt.Printf("%T\n", v)default:fmt.Printf("default")}
}

(2)、case 字句后面可以跟非接口类型名,也可以跟接口类型名,匹配是按照 case 子句的顺序进行的。

  • 如果 case 后面是一个接口类型名,且接口变量i绑定的实例类型实现了该接口类型的方法,则匹配成,v的类

    型是接口类型,v底层绑定的实例是i绑定具体类型实例的副本。

  • 如果 case 后面是一个具体类型名,且接口变量i绑定的实例类型和该具体类型相同,则匹配成功,此时v 就是

    该具体类型变量,v的值是i绑定的实例值的副本。

  • 如果 case 后面跟着多个类型,使用逗号分隔,接口变量i绑定的实例类型只要和其中一个类型匹配,则直接使

    用o赋值给v,相当于 v:=o。这个语法有点奇怪,按理说编译器不应该允许这种操作,语言实现者可能想让

    type switch 语句和普通的 switch 语句保持一样的语法规则,允许发生这种情况。

  • 如果所有的case字句都不满足,则执行 default 语句,此时执行的仍然是 v:=o,最终v的值是o。此时使用v没

    有任何意义。

  • fallthrough 语句不能在 Type Switch 语句中使用。

package mainimport ("fmt""io""log""os"
)func main() {var i io.Reader// 此处i是为未初始化的接口变量,所以v为nilswitch v := i.(type) {case nil:// <nil>fmt.Printf("%T\n", v)default:fmt.Printf("default")}f, err := os.OpenFile("notes.txt", os.O_RDWR|os.O_CREATE, 0755)if err != nil {log.Fatal(err)}defer f.Close()i = fswitch v := i.(type) {// i的绑定的实例是*osFile类型,实现了io.ReadWriter接口,所以下面case匹配成功case io.ReadWriter:// v是io.ReadWriter接口类型,所以可以调用Write方法v.Write([]byte("io.ReadWriter\n"))// Type Switch Result: io.ReadWriterfmt.Println("Type Switch Result: io.ReadWriter")// 由于上一个case已经匹配,就算这个case也匹配,也不会走到这里case *os.File:v.Write([]byte("*os.File\n"))fmt.Println("Type Switch Result: *os.File")//这里可以调用具体类型方法v.Sync()default:fmt.Println("Type Switch Result: unknown")return}switch v := i.(type) {// 匹配成功,v的类型就是具体类型*os.Filecase *os.File:v.Write([]byte("*os.File\n"))// Type Switch Result: *os.Filefmt.Println("Type Switch Result: *os.File")v.Sync()//由于上一个case已经匹配,就算这个case也匹配,也不会走到这里case io.ReadWriter://v是io.ReadWriter接口类型,所以可以调用Write方法v.Write([]byte("io.ReadWriter\n"))fmt.Println("Type Switch Result: io.ReadWriter")default:fmt.Println("Type Switch Result: unknown")return}switch v := i.(type) {//多个类型,f满足其中任何一个就算匹配case *os.File, io.ReadWriter:// 此时相当于执行力v := i ,v和i是等价的,使用v没有意义。if v == i {// truefmt.Println(true)}default:return}
}
# 程序输出
<nil>
Type Switch Result: io.ReadWriter
Type Switch Result: *os.File
true
package mainimport ("fmt"
)func main() {var a inta = 10// the type of a is intgetType(a)
}func getType(a interface{}) {switch a.(type) {case int:fmt.Println("the type of a is int")case string:fmt.Println("the type of a is string")case float64:fmt.Println("the type of a is float")default:fmt.Println("unknown type")}
}
# 程序输出
the type of a is int

相关文章:

Go语言断言和类型查询

Go语言断言和类型查询 1、类型断言 类型断言(Type Assertion)是一个使用在接口值上的操作&#xff0c;用于检查接口类型变量所持有的值是否实现了期望的接 口或者具体的类型。 在Go语言中类型断言的语法格式如下&#xff1a; // i.(TypeNname) value, ok : x.(T)其中&…...

02 Deep learning algorithm

Neural Networks target&#xff1a; inference&#xff08;prediction&#xff09;training my own modelpractical advice for building machine learning systemdecision Tress application: speech&#xff08;语音识别&#xff09; ----> images(计算机视觉)—> t…...

代码随想录算法训练营第二十四天 | 回溯算法

理论基础 代码随想录原文 什么是回溯法 回溯也可以叫做回溯搜索法&#xff0c;它是一种搜索的方式。 回溯是递归的副产品&#xff0c;只要有递归就会有回溯。 回溯法的效率 虽然回溯法很难&#xff0c;不好理解&#xff0c;但是回溯法并不是什么高效的算法。因为回溯的本…...

Spring Cloud Gateway 缓存区异常

目录 1、问题背景 2、分析源码过程 3、解决办法 最近在测试环境spring cloud gateway突然出现了异常&#xff0c;在这里记录一下&#xff0c;直接上干货 1、问题背景 测试环境spring cloud gateway遇到以下异常 DataBufferLimitException: Exceeded limit on max bytes t…...

Spring Boot依赖版本声明

链接 官网 Spring Boot文档官网&#xff1a;​​​​​​https://docs.spring.io/spring-boot/docs/https://docs.spring.io/spring-boot/docs/ Spring Boot 2.0.7.RELEASE Spring Boot 2.0.7.RELEASE reference相关&#xff1a;https://docs.spring.io/spring-boot/docs/2.…...

Java项目:109SpringBoot超市仓管系统

博主主页&#xff1a;Java旅途 简介&#xff1a;分享计算机知识、学习路线、系统源码及教程 文末获取源码 一、项目介绍 超市仓管系统基于SpringBootMybatis开发&#xff0c;系统使用shiro框架做权限安全控制&#xff0c;超级管理员登录系统后可根据自己的实际需求配角色&…...

【React系列】Redux(三) state如何管理

本文来自#React系列教程&#xff1a;https://mp.weixin.qq.com/mp/appmsgalbum?__bizMzg5MDAzNzkwNA&actiongetalbum&album_id1566025152667107329) 一. reducer拆分 1.1. reducer代码拆分 我们来看一下目前我们的reducer&#xff1a; function reducer(state ini…...

3D 纹理的综合指南

在线工具推荐&#xff1a;3D数字孪生场景编辑器 - GLTF/GLB材质纹理编辑器 - 3D模型在线转换 - Three.js AI自动纹理开发包 - YOLO 虚幻合成数据生成器 - 三维模型预览图生成器 - 3D模型语义搜索引擎 我们经常看到超现实主义的视频游戏和动画电影角色出现在屏幕上。他们皮肤上的…...

LLM之RAG实战(十一)| 使用Mistral-7B和Langchain搭建基于PDF文件的聊天机器人

在本文中&#xff0c;使用LangChain、HuggingFaceEmbeddings和HuggingFace的Mistral-7B LLM创建一个简单的Python程序&#xff0c;可以从任何pdf文件中回答问题。 一、LangChain简介 LangChain是一个在语言模型之上开发上下文感知应用程序的框架。LangChain使用带prompt和few-…...

VLOOKUP的使用方法

VLOOKUP是Excel中一个非常有用的函数&#xff0c;用于在一个表格或范围中查找某个值&#xff0c;并返回该值所在行或列的相应数据。 VLOOKUP函数的基本语法如下&#xff1a; VLOOKUP(lookup_value, table_array, col_index_num, [range_lookup])lookup_value&#xff1a;要查…...

数据加密、端口管控、行为审计、终端安全、整体方案解决提供商

PC端访问地址&#xff1a; https://isite.baidu.com/site/wjz012xr/2eae091d-1b97-4276-90bc-6757c5dfedee 以下是关于这几个概念的解释&#xff1a; 数据加密&#xff1a;这是一种通过加密算法和密钥将明文转换为密文&#xff0c;以及通过解密算法和解密密钥将密文恢复为明文…...

编码器原理详解

编码器 什么是编码器 编码器可以用来将信息编码成为二进制代码&#xff0c;有点类似于取代号&#xff0c;人为的将二进制代码与对应的信息联系起来。 如下图所示&#xff1a; 假设有这三种情况会发生&#xff0c;且每次只发生一种情况 为了给这三种情况做一个区分&#xff…...

linux下docker搭建mysql8

1&#xff1a;环境信息 centos 7,mysql8 安装docker环境 2.创建mysql容器 2.1 拉取镜像 docker pull mysql:8.0.23 2.2 查询镜像拉取成功 docker images 2.3 创建挂载的目录文件 mkdir /usr/mysql8/conf mkdir /usr/mysql8/data ##给data文件赋予操作权限 chmod 777 /…...

书生·浦语大模型实战1

书生浦语大模型全链路开源体系 视频链接&#xff1a;书生浦语大模型全链路开源体系_哔哩哔哩_bilibili 大模型之所以能收到这么高的关注度&#xff0c;一个重要原因是大模型是发展通用人工智能的重要途径 深度信念网络&#xff1a; &#xff08;1&#xff09;又被称为贝叶斯网…...

前端JS加密对抗由浅入深-1

前言&#xff1a; 本文主要讲解&#xff0c;针对前端加密数据传输站点&#xff0c;如何进行动态调试以获取加密算法、秘钥&#xff0c;本次实验不涉及漏洞挖掘&#xff0c;仅为学习演示&#xff0c;环境为本地搭建环境 此次站点加密方式为AES加密方式&#xff0c;现如今越来越…...

八股文打卡day17——计算机网络(17)

面试题&#xff1a;拥塞控制是怎么实现的&#xff1f; 我的回答&#xff1a; 1.慢启动 在连接刚建立的时候&#xff0c;会缓慢调大滑动窗口的大小&#xff0c;从而加大网络传输速率&#xff0c;避免速率太快&#xff0c;造成拥塞。 2.拥塞避免 慢启动之后&#xff0c;会进入拥…...

Java-经典算法-logcat获取数据

1 需求 2 语法 3.1 示例&#xff1a;打印本次查询数据 import java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader;/*** 功能&#xff1a;adb logcat -b main -s PRIVA_LOG -d*/ public class Test {public …...

APache 网页优化

技能目标&#xff1a; 掌握 Apache 网页压缩 掌握 Apache 网页缓存 掌握 Apache 网页防盗链 掌握 Apache 隐藏版本信息 4.1 网页压缩与缓存 在使用 Apache 作为 Web 服务器的过程中&#xff0c;只有对 Apache 服务器进行适当的优化配 置&…...

C语言实现关键字匹配算法(复制即用)

文章目录 前言功能要求运行截图全部代码 前言 无套路&#xff0c;均已上机通过&#xff0c;求个关注求个赞&#xff0c;提供答疑解惑服务。 功能要求 一份C源代码存储在一个文本文件中&#xff0c;请统计该文件中关键字出现的频度&#xff0c;并按此频度对关键字进行排序。要…...

【大数据】安装 Zookeeper 单机版

安装 Zookeeper 单机版 下面安装 Zookeeper&#xff0c;由于它是 Apache 的一个顶级项目&#xff0c;所以域名是 zookeeper.apache.org&#xff0c;所有 Apache 的顶级项目的官网都是以项目名 .apache.org 来命名的。 点击 Download 即可下载&#xff0c;这里我们选择的版本是 …...

Oracle查询表空间大小

1 查询数据库中所有的表空间以及表空间所占空间的大小 SELECTtablespace_name,sum( bytes ) / 1024 / 1024 FROMdba_data_files GROUP BYtablespace_name; 2 Oracle查询表空间大小及每个表所占空间的大小 SELECTtablespace_name,file_id,file_name,round( bytes / ( 1024 …...

(二)TensorRT-LLM | 模型导出(v0.20.0rc3)

0. 概述 上一节 对安装和使用有个基本介绍。根据这个 issue 的描述&#xff0c;后续 TensorRT-LLM 团队可能更专注于更新和维护 pytorch backend。但 tensorrt backend 作为先前一直开发的工作&#xff0c;其中包含了大量可以学习的地方。本文主要看看它导出模型的部分&#x…...

服务器硬防的应用场景都有哪些?

服务器硬防是指一种通过硬件设备层面的安全措施来防御服务器系统受到网络攻击的方式&#xff0c;避免服务器受到各种恶意攻击和网络威胁&#xff0c;那么&#xff0c;服务器硬防通常都会应用在哪些场景当中呢&#xff1f; 硬防服务器中一般会配备入侵检测系统和预防系统&#x…...

全球首个30米分辨率湿地数据集(2000—2022)

数据简介 今天我们分享的数据是全球30米分辨率湿地数据集&#xff0c;包含8种湿地亚类&#xff0c;该数据以0.5X0.5的瓦片存储&#xff0c;我们整理了所有属于中国的瓦片名称与其对应省份&#xff0c;方便大家研究使用。 该数据集作为全球首个30米分辨率、覆盖2000–2022年时间…...

智能在线客服平台:数字化时代企业连接用户的 AI 中枢

随着互联网技术的飞速发展&#xff0c;消费者期望能够随时随地与企业进行交流。在线客服平台作为连接企业与客户的重要桥梁&#xff0c;不仅优化了客户体验&#xff0c;还提升了企业的服务效率和市场竞争力。本文将探讨在线客服平台的重要性、技术进展、实际应用&#xff0c;并…...

土地利用/土地覆盖遥感解译与基于CLUE模型未来变化情景预测;从基础到高级,涵盖ArcGIS数据处理、ENVI遥感解译与CLUE模型情景模拟等

&#x1f50d; 土地利用/土地覆盖数据是生态、环境和气象等诸多领域模型的关键输入参数。通过遥感影像解译技术&#xff0c;可以精准获取历史或当前任何一个区域的土地利用/土地覆盖情况。这些数据不仅能够用于评估区域生态环境的变化趋势&#xff0c;还能有效评价重大生态工程…...

华硕a豆14 Air香氛版,美学与科技的馨香融合

在快节奏的现代生活中&#xff0c;我们渴望一个能激发创想、愉悦感官的工作与生活伙伴&#xff0c;它不仅是冰冷的科技工具&#xff0c;更能触动我们内心深处的细腻情感。正是在这样的期许下&#xff0c;华硕a豆14 Air香氛版翩然而至&#xff0c;它以一种前所未有的方式&#x…...

JavaScript基础-API 和 Web API

在学习JavaScript的过程中&#xff0c;理解API&#xff08;应用程序接口&#xff09;和Web API的概念及其应用是非常重要的。这些工具极大地扩展了JavaScript的功能&#xff0c;使得开发者能够创建出功能丰富、交互性强的Web应用程序。本文将深入探讨JavaScript中的API与Web AP…...

C语言中提供的第三方库之哈希表实现

一. 简介 前面一篇文章简单学习了C语言中第三方库&#xff08;uthash库&#xff09;提供对哈希表的操作&#xff0c;文章如下&#xff1a; C语言中提供的第三方库uthash常用接口-CSDN博客 本文简单学习一下第三方库 uthash库对哈希表的操作。 二. uthash库哈希表操作示例 u…...

Proxmox Mail Gateway安装指南:从零开始配置高效邮件过滤系统

&#x1f49d;&#x1f49d;&#x1f49d;欢迎莅临我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 推荐&#xff1a;「storms…...