首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

encoding/binary

  • import "encoding/binary"
  • 概述
  • 索引
  • 示例

概述

软件包二进制实现了数字和字节序列之间的简单转换以及 varint 的编码和解码。

数字通过读取和写入固定大小的值进行翻译。固定大小的值可以是固定大小的算术类型(bool,int8,uint8,int16,float32,complex64,...),也可以是只包含固定大小值的数组或结构。

varint 函数使用可变长度编码对单个整数值进行编码和解码;较小的值需要较少的字节。有关规范,请参阅https://developers.google.com/protocol-buffers/docs/encoding

此包倾向于简化而不是效率。需要高性能序列化的客户端,尤其是大型数据结构的客户端,应该考虑更高级的解决方案,如 encoding/gob 包或协议缓冲区。

索引

  • 常量
  • 变量
  • func PutUvarint(buf []byte, x uint64) int
  • func PutVarint(buf []byte, x int64) int
  • func Read(r io.Reader, order ByteOrder, data interface{}) error
  • func ReadUvarint(r io.ByteReader) (uint64, error)
  • func ReadVarint(r io.ByteReader) (int64, error)
  • func Size(v interface{}) int
  • func Uvarint(buf []byte) (uint64, int)
  • func Varint(buf []byte) (int64, int)
  • func Write(w io.Writer, order ByteOrder, data interface{}) error
  • type ByteOrder

示例

ByteOrder (Get) ByteOrder (Put) PutUvarint PutVarint Read Uvarint Varint Write Write (Multi)

包文件

常量

MaxVarintLenN 是 varint 编码的 N 位整数的最大长度。

const (
        MaxVarintLen16 = 3
        MaxVarintLen32 = 5
        MaxVarintLen64 = 10
)

变量

BigEndian 是 ByteOrder 的大端实现。

var BigEndian bigEndian

LittleEndian 是 ByteOrder 的小端实现。

var LittleEndian littleEndian

func PutUvarint(查看源代码)

func PutUvarint(buf []byte, x uint64) int

PutUvarint 将 uint64 编码到 buf 中,并返回写入的字节数。如果缓冲区太小,PutUvarint 会慌乱(panic)。

示例

package main

import (
	"encoding/binary"
	"fmt"
)

func main() {
	buf := make([]byte, binary.MaxVarintLen64)

	for _, x := range []uint64{1, 2, 127, 128, 255, 256} {
		n := binary.PutUvarint(buf, x)
		fmt.Printf("%x\n", buf[:n])
	}
}

func PutVarint(查看源代码)

func PutVarint(buf []byte, x int64) int

PutVarint 将 int64 编码为 buf 并返回写入的字节数。如果缓冲区太小,PutVarint 会慌乱(panic)。

示例

package main

import (
	"encoding/binary"
	"fmt"
)

func main() {
	buf := make([]byte, binary.MaxVarintLen64)

	for _, x := range []int64{-65, -64, -2, -1, 0, 1, 2, 63, 64} {
		n := binary.PutVarint(buf, x)
		fmt.Printf("%x\n", buf[:n])
	}
}
func Read(r io.Reader, order ByteOrder, data interface{}) error

读取从 r 读取结构化二进制数据到数据。数据必须是指向固定大小值或固定大小值的指针。从 r 读取的字节使用指定的字节顺序解码并写入数据的连续字段。当解码布尔值时,零字节被解码为假,并且任何其他非零字节被解码为真。在读入结构时,跳过带空白(_)字段名称的字段的字段数据;即空白字段​​名称可用于填充。读入结构时,必须导出所有非空白字段或读取可能会出现混乱。

只有在没有字节被读取的情况下,错误才是 EOF。如果在读取一些但不是全部字节后发生 EOF,则 Read 返回 ErrUnexpectedEOF。

示例

package main

import (
	"bytes"
	"encoding/binary"
	"fmt"
)

func main() {
	var pi float64
	b := []byte{0x18, 0x2d, 0x44, 0x54, 0xfb, 0x21, 0x09, 0x40}
	buf := bytes.NewReader(b)
	err := binary.Read(buf, binary.LittleEndian, &pi)
	if err != nil {
		fmt.Println("binary.Read failed:", err)
	}
	fmt.Print(pi)
}

func ReadUvarint(查看源代码)

func ReadUvarint(r io.ByteReader) (uint64, error)

ReadUvarint 从 r 读取一个编码的无符号整数并将其作为 uint64 返回。

func ReadVarint(查看源代码)

func ReadVarint(r io.ByteReader) (int64, error)

ReadVarint 从 r 中读取一个已编码的有符号整数并将其作为 int64 返回。

func Size(v interface{}) int

Size 返回 Write 将生成的值,以便对值 v 进行编码,该值必须是固定大小的值或固定大小的值片段或指向此类数据的指针。如果 v 不是这些,则 Size 返回-1。

func Uvarint(buf []byte) (uint64, int)

Uvarint 从 buf 解码 uint64 并返回该值和读取的字节数(> 0)。如果发生错误,则该值为0,并且字节数n <= 0意味着:

n == 0:buf太小了
n <0:大于64位的值(溢出)
        和-n是读取的字节数

示例

package main

import (
	"encoding/binary"
	"fmt"
)

func main() {
	inputs := [][]byte{
		[]byte{0x01},
		[]byte{0x02},
		[]byte{0x7f},
		[]byte{0x80, 0x01},
		[]byte{0xff, 0x01},
		[]byte{0x80, 0x02},
	}
	for _, b := range inputs {
		x, n := binary.Uvarint(b)
		if n != len(b) {
			fmt.Println("Uvarint did not consume all of in")
		}
		fmt.Println(x)
	}
}
func Varint(buf []byte) (int64, int)

Varint 从 buf 解码 int64 并返回该值和读取的字节数(> 0)。如果发生错误,则值为0,并且字节数 n <= 0,其含义如下:

n == 0:buf太小了
n <0:大于64位的值(溢出)
        和-n是读取的字节数

示例

package main

import (
	"encoding/binary"
	"fmt"
)

func main() {
	inputs := [][]byte{
		[]byte{0x81, 0x01},
		[]byte{0x7f},
		[]byte{0x03},
		[]byte{0x01},
		[]byte{0x00},
		[]byte{0x02},
		[]byte{0x04},
		[]byte{0x7e},
		[]byte{0x80, 0x01},
	}
	for _, b := range inputs {
		x, n := binary.Varint(b)
		if n != len(b) {
			fmt.Println("Varint did not consume all of in")
		}
		fmt.Println(x)
	}
}
func Write(w io.Writer, order ByteOrder, data interface{}) error

写将数据的二进制表示写入 w。数据必须是固定大小的值或固定大小的值片段,或指向这些数据的指针。布尔值编码为一个字节:1 为真,0 为假。写入 w 的字节使用指定的字节顺序进行编码,并从数据的连续字段中读取。在编写结构时,将为具有空白(_)字段名称的字段写入零值。

示例

package main

import (
	"bytes"
	"encoding/binary"
	"fmt"
	"math"
)

func main() {
	buf := new(bytes.Buffer)
	var pi float64 = math.Pi
	err := binary.Write(buf, binary.LittleEndian, pi)
	if err != nil {
		fmt.Println("binary.Write failed:", err)
	}
	fmt.Printf("% x", buf.Bytes())
}

示例(Multi)

package main

import (
	"bytes"
	"encoding/binary"
	"fmt"
)

func main() {
	buf := new(bytes.Buffer)
	var data = []interface{}{
		uint16(61374),
		int8(-54),
		uint8(254),
	}
	for _, v := range data {
		err := binary.Write(buf, binary.LittleEndian, v)
		if err != nil {
			fmt.Println("binary.Write failed:", err)
		}
	}
	fmt.Printf("%x", buf.Bytes())
}

type ByteOrder(查看源代码)

ByteOrder 指定如何将字节序列转换为 16,32 或 64 位无符号整数。

type ByteOrder interface {
        Uint16([]byte) uint16
        Uint32([]byte) uint32
        Uint64([]byte) uint64
        PutUint16([]byte, uint16)
        PutUint32([]byte, uint32)
        PutUint64([]byte, uint64)
        String() string
}

示例(Get)

package main

import (
	"encoding/binary"
	"fmt"
)

func main() {
	b := []byte{0xe8, 0x03, 0xd0, 0x07}
	x1 := binary.LittleEndian.Uint16(b[0:])
	x2 := binary.LittleEndian.Uint16(b[2:])
	fmt.Printf("%#04x %#04x\n", x1, x2)
}

示例 (Put)

package main

import (
	"encoding/binary"
	"fmt"
)

func main() {
	b := make([]byte, 4)
	binary.LittleEndian.PutUint16(b[0:], 0x03e8)
	binary.LittleEndian.PutUint16(b[2:], 0x07d0)
	fmt.Printf("% x\n", b)
}

扫码关注腾讯云开发者

领取腾讯云代金券