上个帖子总结了TCP协议下简单的的C/S模型,现在来看一下UDP协议下的C/S模型,TCP和UDP的异同点下图清晰可见。
因此TCP和UDP各有优缺点,选择什么协议进行开发得根据实际情况分析。
值得一提的是,UDP的客户端实现和TCP的客户端实现可以说是一模一样的,具体可进入我的上一个帖子参考: [golang]实现Tcp协议之简单C/S模型
但是UDP服务器和TCP略有不同!
由于UDP是“无连接”的,所以,服务器端不需要额外创建监听套接字,只需要指定好IP和port,然后监听该地址,等待客户端与之建立连接,即可通信,且UDP服务器不需要并发,也可以说本身就支持并发。
进入代码前,我们先看一下UDP服务器实现所需四个关键函数,按照服务器实现顺序给出,如下:
1)创建监听地址:
func ResolveUDPAddr(network, address string) (*UDPAddr, error)
2)创建用户通信的socket:
func ListenUDP(network string, laddr *UDPAddr) (*UDPConn, error)
3)接收udp数据:
func (c *UDPConn) ReadFromUDP(b []byte) (int, *UDPAddr, error)
4)写出数据到udp:
func (c *UDPConn) WriteToUDP(b []byte, addr *UDPAddr) (int, error)
下面让我们带着这四个函数一起走进具体代码
package main
import (
"net"
"fmt"
"strings"
)
func main() {
//创建监听的地址,并且指定udp协议,返回一个UDP地址和一个错误信息
//我们使用127.0.0.1:6000是本机的回送地址作为师范,可以观察效果
addr,err:=net.ResolveUDPAddr("udp","127.0.0.1:6666")
//接收一下错误信息
if err!=nil {
fmt.Println("resolveudpaddr err", err)
return
}
//创建用户通信的socket,需要用到上面监听函数的返回值,作为此函数的参数
conn,err:=net.ListenUDP("udp",addr)
if err!=nil {
fmt.Println("listen err",err)
return
}
//延时调用关闭
defer conn.Close()
buf:=make([]byte,1024)
for {
//接收udp数据,这里还是会返回一个udp地址,处理数据后发送给这个地址
n,udpaddr,err:=conn.ReadFromUDP(buf)
if n==0 {
fmt.Printf("用户%s退出\n",conn.RemoteAddr().String())
break
}
if err!=nil {
fmt.Println("read err",err)
return
}
/*写数据到udp地址,这里只是一个事例,大家可以做不同
的数据处理后再发送,但注意只能接受字符切片类型作为函数参数*/
_,err=conn.WriteToUDP((buf[:n]),udpaddr)
if err!=nil{
fmt.Println("writeudp err:",err)
return
}
}
}
有任何问题都可以在下面给我留言哦