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

【启程Golang之旅】网络编程与反射

欢迎来到Golang的世界!在当今快节奏的软件开发领域,选择一种高效、简洁的编程语言至关重要。而在这方面,Golang(又称Go)无疑是一个备受瞩目的选择。在本文中,带领您探索Golang的世界,一步步地了解这门语言的基础知识和实用技巧。

目录

初识网络编程

初识反射


初识网络编程

把分布在不同地理区域的计算机与专门的外部设备用通信线路互连成一个规模大、功能强的网络系统,从而使众多的计算机可以方便地互相传递信息、共享硬件、软件、数据信息等资源。设备之间在网络中进行数据的传输,发送/接收数据。

网络:两台或者两台以上计算机就可以构成网络,如下图所示:

设备之间进行传输数据的时候,必须遵循一定的通讯协议规则,具体如下所示:

接下来我们就网络通信的流程写一下网络编程实现的过程,如下:

创建客户端:调用Dial函数实现创建客户端,示例代码如下所示:

func main() {// 打印fmt.Println("客户端启动。。。")// 调用Dial函数,参数需要指定tcp协议,需要指定服务器端的IP+PORTcon, err := net.Dial("tcp", "127.0.0.1:8888")if err != nil {fmt.Println("连接失败, err = ", err)} else {// 打印连接成功fmt.Println("连接成功, con = ", con)}
}

创建服务器端:调用Listen函数实现创建服务器端,示例代码如下所示:

func main() {// 打印fmt.Println("服务器端启动。。。")// 进行监听:需要指定服务器端TCP协议,服务器端的IP+PORTlisten, err := net.Listen("tcp", "127.0.0.1:8888")if err != nil {fmt.Println("监听失败, err = ", err)return}// 监听成功,等待客户端的连接// 循环等待客户端的连接for {con, err1 := listen.Accept()if err1 != nil {fmt.Println("等待客户端连接失败, err = ", err1)return} else {// 连接成功fmt.Printf("等待连接成功,con = %v, 接收到的客户端信息:%v \n", con, con.RemoteAddr().String())}}
}

连接测试:接下来我们开始启动我们的客户端和服务器端,这里我们首先启动服务器端,然后启动客户端对服务器端进行访问,服务器端就等待客户端的访问连接即可,画面如下所示:

发送数据:上面演示了客户端与服务器端的连接,接下来我们开始在客户端设置一些数据然后发送给服务器端,让服务器端去接收到客户端发送过来的数据,示例代码如下所示,由于客户端发送一次数据就关闭了,所以服务器端报出客户端的连接意外关闭的err,这个忽视就行。

具体的代码如下所示:

// 客户端
package mainimport ("bufio""fmt""net""os"
)func main() {// 打印fmt.Println("客户端启动。。。")// 调用Dial函数,参数需要指定tcp协议,需要指定服务器端的IP+PORTcon, err := net.Dial("tcp", "127.0.0.1:8000")if err != nil {fmt.Println("连接失败, err = ", err)} else {// 打印连接成功fmt.Println("连接成功, con = ", con)}// 通过客户端发送单行数据,然后退出reader := bufio.NewReader(os.Stdin) // os.Stdin代表终端标准输入// 从终端读取一行用户输入的信息str, err := reader.ReadString('\n')if err != nil {fmt.Println("终端输入失败, err = ", err)}// 将用户输入的信息发送给服务器端con1, err1 := con.Write([]byte(str)) // []byte将字符串转换为字节数组if err1 != nil {fmt.Println("连接失败, err = ", err1)}// 打印发送成功fmt.Printf("发送成功,发送%d个字节\n", con1)
}// 服务器端
package mainimport ("fmt""net"
)func process(con net.Conn) {// 连接数据完要进行关闭defer con.Close()for {// 创建一个切片,用于接收客户端的数据buf := make([]byte, 1024)// 接收客户端的数据n, err := con.Read(buf)if err != nil {fmt.Println("接收客户端数据失败, err = ", err)return}// 打印接收到的数据fmt.Printf("接收到客户端数据:%v \n", string(buf[0:n]))}
}func main() {// 打印fmt.Println("服务器端启动。。。")// 进行监听:需要指定服务器端TCP协议,服务器端的IP+PORTlisten, err := net.Listen("tcp", "127.0.0.1:8000")if err != nil {fmt.Println("监听失败, err = ", err)return}// 监听成功,等待客户端的连接// 循环等待客户端的连接for {con, err1 := listen.Accept()if err1 != nil {fmt.Println("等待客户端连接失败, err = ", err1)return} else {// 连接成功fmt.Printf("等待连接成功,con = %v, 接收到的客户端信息:%v \n", con, con.RemoteAddr().String())}// 准备协程,协程内容不处理客户端服务请求go process(con)}
}

初识反射

在go语言中,反射(Reflection)是指程序在运行时检查变量的类型和值,并且可以修改这些变量的值、调用其方法以及获取其字段的信息的能力。反射是一种强大的元编程工具,可以让程序在运行时动态地获取和操作类型信息,而不需要在编译时确定。在go语言中,反射是通过reflect包来实现的,以下是反射具体能做的一些事:

1)反射可以在运行时动态获取变量的各种信息,比如变量的类型,类别等信息

2)如果是结构体变量,还可以获取到结构体本身的信息(包括结构体的字段、方法)

3)通过反射,可以修改变量的值,可以调用关联的方法。

4)使用反射,需要import("reflect")

反射相关的使用函数可以通过如下的函数进行操作:

1)reflect.TypeOf(变量名),获取变量的类型,返回reflect.Type类型

2)reflect.ValueOf(变量名),获取变量的值,返回reflect.Value类型(reflect.Value是一个结构体类型),通过reflect.Value,可以获取到关于该变量的很多信息。

对基本类型反射

package mainimport ("fmt""reflect"
)// 利用一个函数,函数的参数定义为空接口
func testReflect(i interface{}) {// 1.调用TypeOf()函数,返回reflect.Type类型数据reType := reflect.TypeOf(i)fmt.Println("reType: ", reType)           // reType:  intfmt.Printf("reType的具体类型是: %T \n", reType) // reType的具体类型是: *reflect.rtype// 2.调用ValueOf()函数,返回reflect.Value类型数据reValue := reflect.ValueOf(i)fmt.Println("reValue: ", reValue)        // reValue:  100fmt.Printf("reValue的具体类型是: %T", reValue) // reValue的具体类型是: reflect.Value// reValue转成空接口i2 := reValue.Interface()// 类型断言n := i2.(int)n1 := n + 30fmt.Println("n1: ", n1) // n1:  130}func main() {// 对基本数据类型进行反射var num int = 100testReflect(num)
}

这里可以通过下图深入进行了解反射:

对结构体反射

package mainimport ("fmt""reflect"
)// 利用一个函数,函数的参数定义为空接口
func testReflect(i interface{}) {// 1.调用TypeOf()函数,返回reflect.Type类型数据reType := reflect.TypeOf(i)fmt.Println("reType: ", reType)           // reType:  intfmt.Printf("reType的具体类型是: %T \n", reType) // reType的具体类型是: *reflect.rtype// 2.调用ValueOf()函数,返回reflect.Value类型数据reValue := reflect.ValueOf(i)fmt.Println("reValue: ", reValue)           // reValue:  100fmt.Printf("reValue的具体类型是: %T \n", reValue) // reValue的具体类型是: reflect.Value// reValue转成空接口i2 := reValue.Interface()// 类型断言n, flag := i2.(Student)if flag {fmt.Printf("学生的名字是:%v, 学生的年龄是: %v", n.Name, n.Age) // 学生的名字是:张三, 学生的年龄是: 18}
}// 定义学生结构体
type Student struct {Name stringAge  int
}func main() {// 对结构体反射stu := Student{Name: "张三",Age:  18,}testReflect(stu)
}

得到的结果如下所示:

如果想获取变量的类别,可以看一下如下的示例代码:

package mainimport ("fmt""reflect"
)// 利用一个函数,函数的参数定义为空接口
func testReflect(i interface{}) {// 1.调用TypeOf()函数,返回reflect.Type类型数据reType := reflect.TypeOf(i)// 2.调用ValueOf()函数,返回reflect.Value类型数据reValue := reflect.ValueOf(i)// 获取遍历的类别// (1)reTypek1 := reType.Kind()fmt.Println("reType:", k1) // reType: struct// (2)reValuek2 := reValue.Kind()fmt.Println("reValue:", k2) // reType: struct// 获取变量的类型// reValue转成空接口i2 := reValue.Interface()// 类型断言n, flag := i2.(Student)if flag { // 类型断言成功fmt.Printf("结构体的类型是: %T", n) // 结构体的类型是: main.Student}
}// 定义学生结构体
type Student struct {Name stringAge  int
}func main() {// 对结构体反射stu := Student{Name: "张三",Age:  18,}testReflect(stu)
}

反射修改变量的值:可以参考如下代码

package mainimport ("fmt""reflect"
)// 利用一个函数,函数的参数定义为空接口
func testReflect(i interface{}) {reValue := reflect.ValueOf(i)// 通过SetInt方法,将i的值设置为10reValue.Elem().SetInt(10)
}func main() {// 定义一个基本数据类型var num int = 100testReflect(&num) // 传入指针地址fmt.Println(num)  // 10
}

相关文章:

【启程Golang之旅】网络编程与反射

欢迎来到Golang的世界!在当今快节奏的软件开发领域,选择一种高效、简洁的编程语言至关重要。而在这方面,Golang(又称Go)无疑是一个备受瞩目的选择。在本文中,带领您探索Golang的世界,一步步地了…...

nginx location正则表达式+案例解析

1、nginx常用的正则表达式 ^ :匹配输入字符串的起始位置$ :匹配输入字符串的结束位置 *:匹配前面的字符零次或多次。如“ol*”能匹配“o”及“ol”、“oll” :匹配前面的字符一次或多次。如“ol”能匹配“ol”及“oll”、“olll”…...

【YOLO系列】YOLOv10论文超详细解读(翻译 +学习笔记)

前言 研究AI的同学们面对的一个普遍痛点是,刚开始深入研究一项新技术,没等明白透彻,就又迎来了新的更新版本——就像我还在忙着逐行分析2月份发布的YOLOv9代码,5月底清华的大佬们就推出了全新的v10。。。 在繁忙之余&#xff0…...

植物大战僵尸杂交版2024潜艇伟伟迷

在广受欢迎的游戏《植物大战僵尸》的基础上,我最近设计了一款创新的杂交版游戏,简直是太赞了!这款游戏结合了原有游戏的塔防机制,同时引入新的元素、角色和挑战,为玩家提供了全新的游戏体验。 植物大战僵尸杂交版最新绿…...

白话解读网络爬虫

网络爬虫(Web Crawler),也称为网络蜘蛛、网络机器人或网络蠕虫,是一种自动化程序或脚本,被用来浏览互联网并收集信息。网络爬虫的主要功能是在互联网上自动地浏览网页、抓取内容并将其存储在本地或远程服务器上供后续处…...

支持向量机(SVM): 从理论到实践的指南(1)

支持向量机(SVM)被誉为数据科学领域的重量级算法,是机器学习中不可或缺的工具之一。SVM以其优秀的泛化能力和对高维数据的管理而备受推崇。本文旨在梳理SVM的核心概念以及其在实际场景中的应用。 SVM的核心理念 SVM专注于为二分类问题找到最…...

万字长文|OpenAI模型规范(全文)

本文是继《OpenAI模型规范概览》之后对OpenAI Model Spec的详细描述,希望能对各位从事大模型及RLHF研究的朋友有帮助。万字长文,建议收藏后阅读。 一、概述 在AI的世界里,确保技术的行为符合我们的期望至关重要。OpenAI最近发布了一份名为Mo…...

微服务架构-正向治理与治理效果

目录 一、正向治理 1.1 概述 1.2 效率治理 1.2.1 概述 1.2.2 基于流量录制和回放的测试 1.2.3 基于仿真环境的测试 1.3 稳定性治理 1.3.1 概述 1.3.2 稳定性治理模型 1.3.3 基于容器化的稳定性治理 1.3.3.1 概述 1.3.3.2 测试 1.3.3.3 部署 1.3.3.3.1 概述 1.3.3…...

normalizing flows vs 直方图规定化

normalizing flows名字的由来 The base density P ( z ) P(z) P(z) is usually defined as a multivariate standard normal (i.e., with mean zero and identity covariance). Hence, the effect of each subsequent inverse layer is to gradually move or “flow” the da…...

vite打包优化常用的技巧及思路

面试题:vitevue项目如何进行优化? 什么情况下会去做打包优化?一种是在搭建项目的时候就根据自己的经验把vite相关配置给处理好,另外一种是开发的过程中发现打包出来的静态资源越来越大,导致用户访问的时候资源加载慢&a…...

k8s学习--kubernetes服务自动伸缩之水平收缩(pod副本收缩)HPA详细解释与案例应用

文章目录 前言HPA简介简单理解详细解释HPA 的工作原理监控系统负载模式HPA 的优势使用 HPA 的注意事项应用类型 应用环境1.metircs-server部署2.HPA演示示例(1)部署一个服务(2)创建HPA对象(3)执行压测 前言…...

台式机ubuntu22.04安装nvidia驱动

总结一个极简易的安装方法 正常安装ubuntu 22.04正常更新软件 sudo apt update sudo apt upgrade -y参考ubuntu官方网站的说明https://ubuntu.com/server/docs/nvidia-drivers-installation#/ # 首先检查系统支持驱动的版本号 sudo ubuntu-drivers list我显示的内容如下&…...

C++ 11 【线程库】【包装器】

💓博主CSDN主页:麻辣韭菜💓   ⏩专栏分类:C修炼之路⏪   🚚代码仓库:C高阶🚚   🌹关注我🫵带你学习更多C知识   🔝🔝 目录 前言 一、thread类的简单介绍 get_id…...

可视化数据科学平台在信贷领域应用系列四:决策树策略挖掘

信贷行业的风控策略挖掘是一个综合过程,需要综合考虑风控规则分析结果、效果评估、线上实时监测和业务管理需求等多个方面,以发现和制定有效的信贷风险管理策略。这些策略可能涉及贷款审批标准的调整、贷款利率的制定、贷款额度的设定等,在贷…...

数据查询深分页优化方案

大家好,我是冰河~~ 最近不少小伙伴在实际工作过程中,遇到了单表大数据量分页的问题,问我怎么优化分页查询。其实,这就是典型的深分页问题。今天趁着周末,给大家整理一些在深分页场景的简单处理方案。 一、普通分页查…...

Redis的主从复制

Redis主从复制是 Redis 内置的⼀种数据冗余和备份⽅式,同时也是分发读查询负载的⼀种⽅法。通过主从复制,可以有多个从服务器(Slave )复制⼀个主服务器(Master )的数据。在这个系统中,数据的复制…...

网络安全实战基础——实战工具与攻防环境介绍

一、实战集成工具 1. 虚拟机 VMware Workstation:大家熟知的虚拟机 Virtual Box:开源免费、轻量级 2. Kali Linux 工具集 信息收集 Nmap:免费开放的网络扫描和嗅探包,可探测主机是否在线,扫描主机端口和嗅探网络…...

vue2组件封装实战系列之tag组件

作为本系列的第一篇文章,不会过于的繁杂,并且前期的组件都会是比较简单的基础组件!但是不要忽视这些基础组件,因为纵观elementui、elementplus还是其他的流行组件库,组件库的封装都是套娃式的,很多复杂组件…...

VBA实战(Excel)(4):实用功能整理

1.后台打开Excel 用于查数据,工作中要打开多个表获取数据再关闭的场景,利用此函数可以将excel表格作为后台数据库查询,快速实现客户要求,缺点是运行效率不够高。 Sub openexcel(exl_name As String)If Dir(addr, 16) Empty Then…...

nginx mirror流量镜像详细介绍以及实战示例

nginx mirror流量镜像详细介绍以及实战示例 1.nginx mirror作用2.nginx安装3.修改配置3.1.nginx.conf3.2.conf.d目录下添加default.conf配置文件3.3.nginx配置注意事项3.3.nginx重启 4.测试 1.nginx mirror作用 为了便于排查问题,可能希望线上的请求能够同步到测试…...

Android14 WMS-窗口添加流程(二)-Server端

Android14 WMS-窗口添加流程(一)-Client端-CSDN博客 本文接着上文"Android14 WMS-窗口添加流程(一)-Client端"往下讲。也就是WindowManagerService#addWindow流程。 目录 一. WindowManagerService#addWindow 标志1:mPolicy.checkAddPermission 标志…...

【传知代码】DETR[端到端目标检测](论文复现)

前言:想象一下,当自动驾驶汽车行驶在繁忙的街道上,DETR能够实时识别出道路上的行人、车辆、交通标志等目标,并准确预测出它们的位置和轨迹。这对于提高自动驾驶的安全性、减少交通事故具有重要意义。同样,在安防监控、…...

Edge浏览器十大常见问题,一次性解决!

Edge曾被称为最好用的浏览器,拳打Chrome脚踢firefox, 可如今却隐藏着像是播放卡顿、下载缓慢、广告繁多等诸多问题,不知道各位还在用吗? 今天小编收集整理了Edge浏览器十大烦人问题,并提供简单有效的解决办法,让你的E…...

lubuntu / ubuntu 配置静态ip

一、查看原始网络配置信息 1、获取网卡名称 ifconfig 2、查询网关IP route -n 二、编辑配置文件 去/etc/netplan目录找到配置文件,配置文件名一般为01-network-manager-all.yaml sudo vim /etc/netplan/01-network-manager-all.yaml文件打开后内容如下 # This …...

15、matlab绘图汇总(图例、标题、坐标轴、线条格式、颜色和散点格式设置)

1、plot()函数默认格式画图 代码: x0:0.1:20;%绘图默认格式 ysin(x); plot(x,y) 2、X轴和Y轴显示范围/axis()函数 代码: x0:0.1:20;%绘图默认格式 ysin(x); plot(x,y) axis([0 21 -1.1 1.1])%设置范围 3、网格显示/grid on函数 代码: …...

调试环境搭建(Redis 6.X 版本)

今儿,我们来搭建一个 Redis 调试环境,目标是: 启动 Redis Server ,成功断点调试 Server 的启动过程。使用 redis-cli 启动一个 Client 连接上 Server,并使用 get key 指令,发起一次 key 的读取。 视频可见…...

postgres数据库报错无法写入文件 “base/pgsql_tmp/pgsql_tmp215574.97“: 设备上没有空间

解决思路: base/pgsql_tmp下临时表空间不够 需要新建一个临时表空间指定到根目录之外的其他目录 并且修改默认临时表空间参数 解决方法: select * from pg_settings where name temp_tablespaces;mkdir /home/postgres/tbs_tmp CREATE TABLESPACE tbs_t…...

力扣2762. 不间断子数组

力扣2762. 不间断子数组 multiset法 multiset&#xff1a;元素从小到大排序 begin()返回头指针 (最小)rbegin()返回尾指针 (最大) class Solution {public:long long continuousSubarrays(vector<int>& nums) {int n nums.size();long long res 0;multiset<…...

OpenCV学习(4.8) 图像金字塔

1.目的 在这一章当中&#xff0c; 我们将了解图像金字塔。我们将使用图像金字塔创建一个新的水果&#xff0c;“Orapple”我们将看到这些功能&#xff1a; cv.pyrUp&#xff08;&#xff09; &#xff0c; cv.pyrDown&#xff08;&#xff09; 在通常情况下我们使用大小恒定…...

【TB作品】msp430f5529单片机,dht22,温湿度传感器,OLED显示屏

使用DHT22温湿度传感器和OLED显示屏的单片机项目 博客名称 利用MSP430单片机读取DHT22并显示温湿度 作品功能 本项目利用MSP430单片机读取DHT22温湿度传感器的数据&#xff0c;并将温湿度信息显示在OLED显示屏上。通过这个项目&#xff0c;您可以学习如何使用单片机与传感器…...

南山做网站多少钱/可以进入任何网站的浏览器

上一篇的内容中&#xff0c;我们已经基本上完成了一个简单的项目&#xff0c;现在我们要学习Django中MVT中M的部分 -- 模型模型准确的描述了一条数据&#xff0c;Django使用ORM(对象关系映射)技术来将一个python类映射为数据库的一张表&#xff0c;而类中的每个类属性映射为表中…...

网站建设论文框架/新闻软文发稿平台

我们知道定义一个委托之后&#xff0c;就可以像MyDelegate&#xff08;3&#xff0c;7&#xff09;这样回调方法&#xff0c;其实每一个委托对象都是一个类对象&#xff0c;每一个委托对象中都有一个Invoke的同步成员方法&#xff08;查MSDN得知&#xff09;&#xff0c;系统实…...

做专业课视频课的网站/互联网营销的十五种方式

如何使用 调用头文件<algorithm>中的make_heap函数是某容器内元素堆化&#xff0c;默认使用的比较函数是less<T>()&#xff0c;默认生成大根堆。 若在第三个参数指定比较函数即可以生成不同的堆&#xff0c;对使用great<T>()可以生成小根堆 代码 #include…...

wordpress 主机和域名绑定/域名注册查询入口

subprocess如何避免死锁 如果交互是双工的&#xff0c;即涉及读取和写入&#xff0c;则尤其如此。这种交互可能导致死锁&#xff0c;因为两个进程都可能最终等待另一个进程的输出 您希望从子进程标准输出管道读取&#xff0c;但标准错误管道的缓冲区已满&#xff0c;操作系统希…...

网络工程师题库/seo实战培训视频

因为市场上有许多的SQL管理工具&#xff0c;所以要为SQL项目管理选择工具是一件有挑战性的事。为大家推荐23款SQL工具的精选列表&#xff0c;希望朋友们喜欢。其中几款已经在昨天的SQL查询优化工具一文中&#xff0c;做过推荐。1.Aqua Data StudioAqua Data Studio是一个功能丰…...

大连的网站制作公司/百度一下就知道百度首页

Apache的mod_rewrite是提供了强大URL操作的杀手级的模块&#xff0c;可以实现几乎所有你梦想的URL操作类型&#xff0c;其代价是你必须接受其复杂性&#xff0c;因为mod_rewrite的主要障碍就是初学者不容易理解和运用&#xff0c;即使是Apache专家有时也会发掘出mod_rewrite的新…...