Golang IOT中的数据序列化与解析过程

 更新时间:2023年05月20日 08:59:23   作者:笨笨D幸福  
这篇文章主要介绍了Golang IOT中的数据序列化与解析,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下

Golang IOT中的数据序列化与解析

Golang中对于JSON、XML、HTML、RPC、PB、Thrift等现代化协议都支持的非常好,但是对于IOT领域,用的多的反而是HEX原始数据,如果一个个解析,会是非常麻烦的事情。
所以,对于HEX数据是否有方便好用的打包/解包方法?

目前,比较官方和流行的方式有如下几种:

对于gob和msgpack在IOT一般比较困难,适用性差,探索一下binary的方案。

Binary结构体与二进制

参考: https://www.jb51.net/jiaoben/284968z11.htm

经常有这样的需求,在底层硬件设备通过TCP/UART传输了一堆数据过来,但是都是16进制的,每1-4个字节表示一个数据,然后还有可能有数组一类的数据。从数据类型上存在bool/int8/int16/int32/int64/float32,还有对应的数组。

如果简单地通过16进制操作,当然可以完成,但是维护起来非常费力,如果设备多了就简直时灾难。

所以,是否存在一种类似模板的方案,自动根据某个字节进行数据的解析和转换呢?答案是肯定的!虽然不一定能完全自动化,但是能节约维护的时间和BUG。

假设我们有这样一个HEX数据

Message: Byte. 假设N=4
  ┌──────┬──────┬────────┬──────────┬──────────┬───────┐
  │ Id: 1│Cmd: 1│ Addr: 2│Length: 2 │Data: 2*N │ CRC:2 │
  └──────┴──────┴────────┴──────────┴──────────┴───────┘

对应数据Data根据Cmd的值不同,有不同的长度和意义。该如何Design这个解析处理呢?

package main
import (
	"bytes"
	"encoding/binary"
	"fmt"
)
// message的基础结构,继承后使用
// size = 6
type CmdMsgBaseHeader struct {
	Idx  uint8  // 设备模块的唯一ID,从1-254,255表示广播
	Cmd  uint8  // 命令值,表示不同类型的消息
	Addr uint16 // 数据地址,2个字节,高字节在前。大端字节序(big endian)
	Len  uint16 // 返回的真实数据长度,以2个字节为一个单位
	//Data [N]uint8 // RAW数据,根据Cmd和Addr区分作用。一般作为继承数据使用。固定size。
	//CRC  [2]uint8 // CRC校验
}
// 假设的 数据1
// size = 2 + 2*Len = 10
type CmdMsg_IO_Status struct {
	CmdMsgBaseHeader
	Data [4]uint16
	CRC  [2]uint8
}
func main() {
	a := CmdMsg_IO_Status{}
	b := []uint8{0x01, 0x09, 0x02, 0x01, 0x00, 0x04 /*Data*/, 0x01, 0x02, 0x01, 0x03, 0x01, 0x04, 0x01, 0x05 /*CRC*/, 0xAC, 0xAC}
	buff := bytes.NewBuffer(b)
    // buff size = 6+10 = 16
	err := binary.Read(buff, binary.BigEndian, &a)
	if err != nil {
		fmt.Println("read error:", err)
		return
	}
	// decode ok
	fmt.Printf("decode: %+v\n", a) // {CmdMsgBaseHeader:{Idx:1 Cmd:9 Addr:513 Len:4} Data:[258 259 260 261] CRC:[172 172]}
}

这样,通过不断定制CmdMsg_IO_Status就可以按照需求解析HEX数据。

到此这篇关于Golang IOT中的数据序列化与解析的文章就介绍到这了,更多相关go数据序列化内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Go测试之.golden文件使用示例详解

    Go测试之.golden文件使用示例详解

    这篇文章主要为大家介绍了Go测试之.golden文件使用示例详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-08-08
  • GoRoutines高性能同时进行多个Api调用实现

    GoRoutines高性能同时进行多个Api调用实现

    这篇文章主要为大家介绍了GoRoutines高性能同时进行多个Api调用实现示例,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-03-03
  • 用Go语言编写一个简单的分布式系统

    用Go语言编写一个简单的分布式系统

    这篇文章主要介绍了用Go语言编写一个简单的分布式系统,文中的代码示例讲解的非常详细,对我们的学习或工作有一定的帮助,感兴趣的小伙伴跟着小编一起来看看吧
    2023-08-08
  • Go Gin中间件的具体使用

    Go Gin中间件的具体使用

    中间件是Gin框架中的一个重要概念,它可以用来处理HTTP请求和响应,或者在处理请求之前和之后执行一些操作,本文主要介绍了Go Gin中间件的具体使用,感兴趣的可以了解一下
    2023-11-11
  • golang cobra使用chatgpt qdrant实现ai知识库

    golang cobra使用chatgpt qdrant实现ai知识库

    这篇文章主要为大家介绍了golang cobra使用chatgpt qdrant实现ai知识库,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-09-09
  • Golang实现自定义时间结构体并支持Json&Gorm

    Golang实现自定义时间结构体并支持Json&Gorm

    因为时区等问题,很多项目需要自定义时区和时间格式,所以这篇文章主要为大家介绍了Golang如何实现自定义时间结构体并支持Json&Gorm,希望对大家有所帮助
    2024-03-03
  • go语言检测文件是否存在的方法

    go语言检测文件是否存在的方法

    这篇文章主要介绍了go语言检测文件是否存在的方法,实例分析了Go语言文件操作的相关技巧,需要的朋友可以参考下
    2015-03-03
  • Go中使用操作符进行数学运算的示例代码

    Go中使用操作符进行数学运算的示例代码

    在编程中有效地执行数学运算是一项需要开发的重要技能,本文主要介绍了Go中使用操作符进行数学运算的示例代码,具有一定的参考价值,感兴趣的可以了解一下
    2023-10-10
  • go 分布式锁简单实现实例详解

    go 分布式锁简单实现实例详解

    这篇文章主要为大家介绍了go 分布式锁简单实现实例详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-09-09
  • Golang使用Decimal库避免运算中精度损失详细步骤

    Golang使用Decimal库避免运算中精度损失详细步骤

    decimal是为了解决Golang中浮点数计算时精度丢失问题而生的一个库,使用decimal库我们可以避免在go中使用浮点数出现精度丢失的问题,下面这篇文章主要给大家介绍了关于Golang使用Decimal库避免运算中精度损失的相关资料,需要的朋友可以参考下
    2023-06-06

最新评论