讲师中心 微信公众号

工具推荐

视频效率加速
AniShort
AniShort

AI短剧协同制作平台

Laper
Laper

剧本策划到成片协作

updream

一键生成高质量推广成片

Seko
Seko

AI短剧一键生成成片

Golang UDP编程指南_无连接的数据报通信实现

陌辰大大_6971

陌辰大大_6971

发布时间:2026-02-23 14:10:03

|

684人浏览过

|

来源于php中文网

原创

UDP服务端应调用SetReadDeadline设置读超时,显式检查os.ErrDeadlineExceeded错误并循环重试;监听需用":端口"而非"localhost";客户端建议用DialUDP保证地址配对;读取时须校验返回长度n防截断。

golang udp编程指南_无连接的数据报通信实现

UDP 服务端怎么避免 readfrom udp 阻塞住整个 goroutine

Go 的 net.UDPConn.ReadFrom 默认是阻塞的,但你写服务端时通常希望它不卡死、能配合 context 或超时控制。直接用 ReadFrom 而不设超时,一个发呆的客户端就能让单个 goroutine 永久挂起。

  • 必须在 UDPConn 上调用 SetReadDeadline 或 SetReadDeadline(注意:UDP 不支持 SetDeadline,只能用带时间的版本)
  • 超时后会返回 readfrom udp: i/o timeout 错误,不是 EOF,要显式判断 errors.Is(err, os.ErrDeadlineExceeded)
  • 别用 for {} 死循环 + ReadFrom —— 一旦出错没处理,goroutine 就废了;应封装成带重试/日志/上下文取消的读循环
  • 示例片段:
    conn, _ := net.ListenUDP("udp", &net.UDPAddr{Port: 8080})
    defer conn.Close()
    buf := make([]byte, 1500)
    for {
        n, addr, err := conn.ReadFrom(buf)
        if err != nil {
            if errors.Is(err, os.ErrDeadlineExceeded) {
                continue // 超时,继续下一轮
            }
            log.Printf("read error: %v", err)
            break
        }
        // 处理 buf[:n] 和 addr
    }

UDP 客户端发包后收不到响应?检查 WriteTo 和 ReadFrom 的地址一致性

UDP 是无连接的,WriteTo 发给谁、ReadFrom 就得从谁那里收 —— 但很多人写客户端时只 WriteTo 一次,然后在同一个 UDPConn 上反复 ReadFrom,结果收的是其他客户端的回包,或者压根没发成功。

  • WriteTo 不会自动绑定远端地址,也不会记住它;每次 ReadFrom 返回的 net.Addr 才是实际来源,必须核对是否和你发往的目标一致
  • 常见错误:发给 127.0.0.1:9000,但 ReadFrom 收到的是 192.168.1.100:9000(比如服务端做了 SNAT 或代理),这时直接丢弃就丢了响应
  • 若需严格配对,建议每次发完立刻 ReadFrom 并比对 addr.String(),或改用 net.DialUDP 建立“伪连接”,之后可用 Write/Read(底层仍走 UDP,但地址被固定)
  • DialUDP 示例:
    c, _ := net.DialUDP("udp", nil, &net.UDPAddr{IP: net.ParseIP("127.0.0.1"), Port: 9000})
    c.Write([]byte("ping"))
    buf := make([]byte, 1024)
    n, _ := c.Read(buf) // 这里只收来自 127.0.0.1:9000 的包

为什么 net.ListenUDP 绑定 localhost 后外部连不上

这是最常被忽略的地址语义问题:"localhost" 解析为 127.0.0.1(IPv4)或 ::1(IPv6),而这两个地址都只响应本机回环流量,外部机器的 UDP 包根本进不来内核协议栈。

Golang Uber Dig
Golang Uber Dig

使用 uber-go/dig 在 Golang 中实现依赖注入——基于反射容器,提供 Provide/Invoke、dig.In/dig.Out 参数与结果对象,支持命名依赖等

下载
  • 想让局域网或公网访问,必须显式监听 ":8080"(即 0.0.0.0:8080)或指定具体网卡 IP,例如 "192.168.1.50:8080"
  • Windows/macOS 上用 localhost 可能“看起来能通”,其实是本地测试绕过了网络栈,不代表真实部署可行
  • 如果服务跑在 Docker 或 Kubernetes 中,还要确认容器端口是否正确 -p 映射,且宿主机防火墙没拦 UDP
  • 验证方式:用另一台机器执行 nc -u your-server-ip 8080,再看服务端日志有没有收到 ReadFrom 的地址记录

UDP 包被截断?关注 ReadFrom 返回的 n 和 MTU

UDP 不保证交付,也不保证不分片 —— 如果应用层数据超过路径 MTU(通常是 1500 字节以太网帧减去 IP+UDP 头),IP 层会分片;而任意一片丢失,整条 UDP 报文就报废。更隐蔽的问题是:接收缓冲区太小,导致 ReadFrom 只读前 N 字节,后面被丢弃,还返回 n 却没报错。

立即学习“go语言免费学习笔记(深入)”;

  • 务必检查 ReadFrom 返回的 n 是否等于预期长度;若小于 len(buf),大概率是包被截断(尤其在高并发或大 payload 场景)
  • 服务端 buffer 建议至少 65535 字节(UDP 最大理论载荷),但实际中 8192–16384 更平衡内存与安全
  • 不要假设“发出去多少,对方一定收到多少”;业务层如需可靠,得自己加序列号、重传、校验(或换 TCP)
  • Linux 下可临时调大接收缓冲区:sysctl -w net.core.rmem_max=262144,但治标不治本
UDP 的“简单”背后全是边界条件:超时控制、地址匹配、监听范围、缓冲区大小、MTU 敏感性……这些地方不显式处理,程序上线后基本靠日志猜问题。

相关文章

编程速学教程(入门课程)
编程速学教程(入门课程)

编程怎么学习?编程怎么入门?编程在哪学?编程怎么学才快?不用担心,这里为大家提供了编程速学教程(入门课程),有需要的小伙伴保存下载就能学习啦!

下载

相关标签:

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

热门AI工具

更多
函子Zion

一款支持AI搭建、可视化编辑和多端发布的全栈无代码开发平台。

创客贴AI

创客贴AI是一款AI图像与设计工具,AI辅助的智能在线设计工具。

讯飞智文

一款面向学习和办公场景的AI文档创作工具,可辅助生成PPT与Word文档,提高资料整理和内容制作效率。

豆包大模型

豆包大模型是一款由字节跳动推出的企业级大语言模型服务平台。

讯飞绘文

讯飞绘文是一款由科大讯飞推出的一站式 AIGC 内容运营平台。

Lovart
Lovart Hot

一款面向视觉设计创作的AI设计平台,可通过智能体和画布工作流辅助制作海报、Logo、网页、PPT及其他视觉内容。

DeepSeek

DeepSeek是一款面向对话、写作、编程和推理场景的AI大模型工具。

WorkBuddy

一款AI办公效率工具,主要用于腾讯云推出的AI原生桌面智能体工作台,适合需要提升相关任务效率的用户。

咔片AIPPT

一款在线AI演示文稿制作工具,可根据主题和内容需求辅助生成PPT结构与页面,提高演示材料制作效率。

相关专题

更多
golang如何定义变量
golang如何定义变量

golang定义变量的方法:1、声明变量并赋予初始值“var age int =值”;2、声明变量但不赋初始值“var age int”;3、使用短变量声明“age :=值”等等。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

539

2024.02.23

golang有哪些数据转换方法
golang有哪些数据转换方法

golang数据转换方法:1、类型转换操作符;2、类型断言;3、字符串和数字之间的转换;4、JSON序列化和反序列化;5、使用标准库进行数据转换;6、使用第三方库进行数据转换;7、自定义数据转换函数。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

616

2024.02.23

golang常用库有哪些
golang常用库有哪些

golang常用库有:1、标准库;2、字符串处理库;3、网络库;4、加密库;5、压缩库;6、xml和json解析库;7、日期和时间库;8、数据库操作库;9、文件操作库;10、图像处理库。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

1296

2024.02.23

golang和python的区别是什么
golang和python的区别是什么

golang和python的区别是:1、golang是一种编译型语言,而python是一种解释型语言;2、golang天生支持并发编程,而python对并发与并行的支持相对较弱等等。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

811

2024.03.05

golang是免费的吗
golang是免费的吗

golang是免费的。golang是google开发的一种静态强类型、编译型、并发型,并具有垃圾回收功能的开源编程语言,采用bsd开源协议。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

1886

2024.05.21

golang结构体相关大全
golang结构体相关大全

本专题整合了golang结构体相关大全,想了解更多内容,请阅读专题下面的文章。

5394

2025.06.09

golang相关判断方法
golang相关判断方法

本专题整合了golang相关判断方法,想了解更详细的相关内容,请阅读下面的文章。

2514

2025.06.10

golang数组使用方法
golang数组使用方法

本专题整合了golang数组用法,想了解更多的相关内容,请阅读专题下面的文章。

4346

2025.06.17

Go-Zero API开发使用教程
Go-Zero API开发使用教程

本专题聚焦Go-Zero的API开发,拆解.api描述文件的语法结构、路由与分组定义、参数绑定与校验规则,说明统一响应体、JWT鉴权、跨域与接口文档生成的落地方式,并给出网关聚合与接口测试的实践建议。

0

2026.11.12

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
Go-Zero框架快速开始指南
Go-Zero框架快速开始指南

共0课时 | 0人学习

Go-Zero官方文档
Go-Zero官方文档

共0课时 | 0人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn