最近一直和硬件打交道,而和这些硬件交互很多用到了socket。于是在使用的过程中同时简单的学习了一下net包的dial。

在go中,大致提供了5种dial,包括:

1.  Dial(network, address string) (Conn, error)

2. DialTCP(network string, laddr, raddr *TCPAddr) (*TCPConn, error)

3. DialUDP(network string, laddr, raddr *UDPAddr) (*UDPConn, error)

4. DialIP(network string, laddr, raddr *IPAddr) (*IPConn, error)

5. DialUnix(network string, laddr, raddr *UnixAddr) (*UnixConn, error)

其中dial是对其他几个的封装,同时实现了Conn接口。

而其他几个,虽然返回TCPConn,UDPConn,IPConn,UnixConn。但是他们的底层是一样的如下图:

最终这几个返回都是对netfd结构体的返回。而且除了DialUnix 其余三个最终都是走的  internetSocket()  只不过在调用这个方法前,各自的处理有一些不同。

而DialUnix最终调用的是一个 unixSocket()。

如果大家想看具体实现,可以去tcpsock,udpsock,ipsock,unixsock这几个文件看看。

因为他们基本都有相同的实现,和相同的返回。所以他们的使用也是基本相同,下面就以dial,tcpdial为例。

//创建连接conn,err := net.Dial("tcp","192.168.1.254:4001")//发送数据conn.Write([]byte{0x00,0x07,0x00,0x00,0x00,0x06,0x01,0x03,0x00,0x00,0x00,0x0A})defer conn.Close()buffer := make([]byte,32)//读取返回数据result,err := conn.Read(buffer)if err != nil {fmt.Println(err)}fmt.Println(result,buffer)
//进行地址化转换tcpAddr,err:=net.ResolveTCPAddr("tcp","192.168.1.254:4001")//创建一个连接conn,err:=net.DialTCP("tcp",nil,tcpAddr)if err != nil {fmt.Println(err)}str := []byte{32, 0, 0, 0, 7, 85, 35, 160, 176, 7, 226, 12, 18, 15, 45, 0}//向连接端发送一个数据_,err=conn.Write(str)if err != nil {fmt.Println(err)}//读取连接端返回来的数据,result,err:=ioutil.ReadAll(conn)if err != nil {fmt.Println(err)}fmt.Println(string(result))

从这两个请求可以看出,dial只需要直接填入连接地址,而dialtcp却需要提前把地址转换为对应的类型才能填入。在dial中,连接会根据你填入的连接类型,自动把地址转换为对应类型地址。

同时,我们还会发现我们dial中用了buffer接收数据,而在dialtcp用了ioutil.ReadAll()返回所有数据。

这两种方法有什么不同,第一种是把buffer填充完后就直接执行后面的代码了,但是buffer的你需要事先定义大小。第二种ioutil.ReadAll()要是拿不到结束符,会一直等到连接超时才执行后面代码。这样就会导致阻塞很长时间。

net包 dial - golang相关推荐

  1. log包在Golang语言的标准库中是怎么使用的?

    Golang 语言的标准库中提供了一个简单的 log 日志包,它不仅提供了很多函数,还定义了一个包含很多方法的类型 Logger.但是它也有缺点,比如不支持区分日志级别,不支持日志文件切割等. 01. ...

  2. net包 listen - golang

    在前面我们简单的了解了一下,如何构建客户端请求,同时简单的了解了他们之间的调用和封装关系.从而在封装方法在满足不了需求时,我们可以使用更底层一级的方法构建自己的需求. 今天我们看一下服务端的一些监听方 ...

  3. 导入gust包体验Golang的声明式编程

    开发者:https://github.com/andeya 作者:https://github.com/GpigZ 地址:https://github.com/andeya/gust gust基本介绍 ...

  4. 【golang程序包推荐分享】分享亿点点golang json操作及myJsonMarshal程序包开发的踩坑经历 :)

    目录[阅读时间:约5分钟] 一.概述 1.Json的作用 2.Go官方 encoding/json 包 3. golang json的主要操作 二.Json Marshal:将数据编码成json字符串 ...

  5. 下载 golang.org/x 包出错不用代理的解决办法

    原文链接:https://www.jianshu.com/p/6fe61053c8aa?utm_campaign=maleskine&utm_content=note&utm_medi ...

  6. Golang sort 包使用

    1.sort包简介 Golang 中的标准库 sort 包为切片及用户定义的集合的排序操作提供了原语.sort包提供了对内置类型切片的排序支持,如 []int切片.[]float64切片和[]stri ...

  7. golang解决TCP粘包问题

    6行代码解决golang TCP粘包 转自:https://studygolang.com/articles/12483 什么是TCP粘包问题以及为什么会产生TCP粘包,本文不加讨论.本文使用gola ...

  8. 简单阅读golang的net/http包和Negroni的源码

    在没文档指导下阅读源码比较麻烦. 我们知道,golang比起c/c++来说,已经内建了http服务的功能,而且因为golang的特性,性能不低. 下面通过阅读net/http的部分源码来看看它是怎么工 ...

  9. golang的unsafe包

    unsafe包主要用于golang编译.其他地方不推荐使用. 结构体的成员在内存中的分配是一段连续的内存,结构体中第一个成员的地址就是这个结构体的地址,也可以认为是相对于这个结构体偏移了0.相同的,这 ...

最新文章

  1. android跑分和ios,安卓评分再高也没用吗 安卓与ios的区别
  2. jsp cookie 中文乱码 的解决方法
  3. 荷兰牛栏 荷兰售价_荷兰的公路货运是如何发展的
  4. Vue + Spring Boot 项目实战(六):使用 Element 辅助前端开发
  5. 软考(2)——看图心想编译原理
  6. 【Flink】解决Flink在测试环境无法保存checkpoint问题
  7. vue-cli watch简单用法
  8. eclipse中修改项目文件夹目录显示结构
  9. @vue/cli 3.0 eslint 转成tslint
  10. getElementById和querySelector方法的区别
  11. android无线投屏到win,无线投影仪怎么连接,看过教程,原来操作这么简单!
  12. C++二维数组的定义及理解
  13. OneApiConnect(一) Fins欧姆龙通讯协议实现源代码
  14. 如何在Microsoft PowerPoint中绘制和操纵箭头
  15. IgA | 对抗病原菌,帮助共生菌定植的“重要开关”
  16. AV1编码器优化技术
  17. 判断各类无盘软件是否处于超管状态
  18. 金仓数据库 KingbaseES 异构数据库移植指南 (4. 应用迁移流程)
  19. Arduino LCD1602电子时钟
  20. CodeForces - 348A E - Mafia

热门文章

  1. SEM(Search Engine Marketing)–
  2. Sentinel流量防卫兵和组成成分
  3. Android Studio 使用Token登录Git
  4. 身材不高穿什么身材不高穿什么
  5. linux打压缩包去掉某个文件夹,linux tar压缩排除某个文件夹的方法
  6. linux中删除特殊名称文件
  7. 云计算HCIP实验-AD域控搭建
  8. matlab中利用function定义复数运算
  9. html页面的基本布局
  10. 几行Python代码实现人像动漫化, 让头像独一无二