protobuf跟json

本文对比了Protobuf与JSON在数据序列化方面的性能差异,通过具体实例展示了两种格式的数据大小及编解码时间,揭示了Protobuf在数据传输效率上的优势。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

//test.pb.go
// Code generated by protoc-gen-go. DO NOT EDIT.
// source: test.proto

package pb

import (
	fmt "fmt"
	proto "github.com/golang/protobuf/proto"
	math "math"
)

// Reference imports to suppress errors if they are not otherwise used.
var _ = proto.Marshal
var _ = fmt.Errorf
var _ = math.Inf

// This is a compile-time assertion to ensure that this generated file
// is compatible with the proto package it is being compiled against.
// A compilation error at this line likely means your copy of the
// proto package needs to be updated.
const _ = proto.ProtoPackageIsVersion3 // please upgrade the proto package

// AgentData
type AgentData struct {
	SubPlayer            []*DownPosition `protobuf:"bytes,1,rep,name=SubPlayer,proto3" json:"SubPlayer,omitempty"`
	Compelte             int32           `protobuf:"varint,2,opt,name=Compelte,proto3" json:"Compelte,omitempty"`
	Level                int32           `protobuf:"varint,3,opt,name=Level,proto3" json:"Level,omitempty"`
	PlayerID             int64           `protobuf:"varint,4,opt,name=PlayerID,proto3" json:"PlayerID,omitempty"`
	Data                 []int32         `protobuf:"varint,5,rep,packed,name=Data,proto3" json:"Data,omitempty"`
	XXX_NoUnkeyedLiteral struct{}        `json:"-"`
	XXX_unrecognized     []byte          `json:"-"`
	XXX_sizecache        int32           `json:"-"`
}

func (m *AgentData) Reset()         { *m = AgentData{} }
func (m *AgentData) String() string { return proto.CompactTextString(m) }
func (*AgentData) ProtoMessage()    {}
func (*AgentData) Descriptor() ([]byte, []int) {
	return fileDescriptor_c161fcfdc0c3ff1e, []int{0}
}

func (m *AgentData) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_AgentData.Unmarshal(m, b)
}
func (m *AgentData) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_AgentData.Marshal(b, m, deterministic)
}
func (m *AgentData) XXX_Merge(src proto.Message) {
	xxx_messageInfo_AgentData.Merge(m, src)
}
func (m *AgentData) XXX_Size() int {
	return xxx_messageInfo_AgentData.Size(m)
}
func (m *AgentData) XXX_DiscardUnknown() {
	xxx_messageInfo_AgentData.DiscardUnknown(m)
}

var xxx_messageInfo_AgentData proto.InternalMessageInfo

func (m *AgentData) GetSubPlayer() []*DownPosition {
	if m != nil {
		return m.SubPlayer
	}
	return nil
}

func (m *AgentData) GetCompelte() int32 {
	if m != nil {
		return m.Compelte
	}
	return 0
}

func (m *AgentData) GetLevel() int32 {
	if m != nil {
		return m.Level
	}
	return 0
}

func (m *AgentData) GetPlayerID() int64 {
	if m != nil {
		return m.PlayerID
	}
	return 0
}

func (m *AgentData) GetData() []int32 {
	if m != nil {
		return m.Data
	}
	return nil
}

// DownPosition
type DownPosition struct {
	PlayerID             int64    `protobuf:"varint,1,opt,name=PlayerID,proto3" json:"PlayerID,omitempty"`
	Pos                  int32    `protobuf:"varint,2,opt,name=Pos,proto3" json:"Pos,omitempty"`
	XXX_NoUnkeyedLiteral struct{} `json:"-"`
	XXX_unrecognized     []byte   `json:"-"`
	XXX_sizecache        int32    `json:"-"`
}

func (m *DownPosition) Reset()         { *m = DownPosition{} }
func (m *DownPosition) String() string { return proto.CompactTextString(m) }
func (*DownPosition) ProtoMessage()    {}
func (*DownPosition) Descriptor() ([]byte, []int) {
	return fileDescriptor_c161fcfdc0c3ff1e, []int{1}
}

func (m *DownPosition) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_DownPosition.Unmarshal(m, b)
}
func (m *DownPosition) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_DownPosition.Marshal(b, m, deterministic)
}
func (m *DownPosition) XXX_Merge(src proto.Message) {
	xxx_messageInfo_DownPosition.Merge(m, src)
}
func (m *DownPosition) XXX_Size() int {
	return xxx_messageInfo_DownPosition.Size(m)
}
func (m *DownPosition) XXX_DiscardUnknown() {
	xxx_messageInfo_DownPosition.DiscardUnknown(m)
}

var xxx_messageInfo_DownPosition proto.InternalMessageInfo

func (m *DownPosition) GetPlayerID() int64 {
	if m != nil {
		return m.PlayerID
	}
	return 0
}

func (m *DownPosition) GetPos() int32 {
	if m != nil {
		return m.Pos
	}
	return 0
}

func init() {
	proto.RegisterType((*AgentData)(nil), "pb.AgentData")
	proto.RegisterType((*DownPosition)(nil), "pb.DownPosition")
}

func init() { proto.RegisterFile("test.proto", fileDescriptor_c161fcfdc0c3ff1e) }

var fileDescriptor_c161fcfdc0c3ff1e = []byte{
	// 186 bytes of a gzipped FileDescriptorProto
	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0xe2, 0x2a, 0x49, 0x2d, 0x2e,
	0xd1, 0x2b, 0x28, 0xca, 0x2f, 0xc9, 0x17, 0x62, 0x2a, 0x48, 0x52, 0x9a, 0xcb, 0xc8, 0xc5, 0xe9,
	0x98, 0x9e, 0x9a, 0x57, 0xe2, 0x92, 0x58, 0x92, 0x28, 0xa4, 0xc7, 0xc5, 0x19, 0x5c, 0x9a, 0x14,
	0x90, 0x93, 0x58, 0x99, 0x5a, 0x24, 0xc1, 0xa8, 0xc0, 0xac, 0xc1, 0x6d, 0x24, 0xa0, 0x57, 0x90,
	0xa4, 0xe7, 0x92, 0x5f, 0x9e, 0x17, 0x90, 0x5f, 0x9c, 0x59, 0x92, 0x99, 0x9f, 0x17, 0x84, 0x50,
	0x22, 0x24, 0xc5, 0xc5, 0xe1, 0x9c, 0x9f, 0x5b, 0x90, 0x9a, 0x53, 0x92, 0x2a, 0xc1, 0xa4, 0xc0,
	0xa8, 0xc1, 0x1a, 0x04, 0xe7, 0x0b, 0x89, 0x70, 0xb1, 0xfa, 0xa4, 0x96, 0xa5, 0xe6, 0x48, 0x30,
	0x83, 0x25, 0x20, 0x1c, 0x90, 0x0e, 0x88, 0x5e, 0x4f, 0x17, 0x09, 0x16, 0x05, 0x46, 0x0d, 0xe6,
	0x20, 0x38, 0x5f, 0x48, 0x88, 0x8b, 0x05, 0xe4, 0x0a, 0x09, 0x56, 0x05, 0x66, 0x0d, 0xd6, 0x20,
	0x30, 0x5b, 0xc9, 0x86, 0x8b, 0x07, 0xd9, 0x72, 0x14, 0xfd, 0x8c, 0x68, 0xfa, 0x05, 0xb8, 0x98,
	0x03, 0xf2, 0x8b, 0xa1, 0x0e, 0x01, 0x31, 0x93, 0xd8, 0xc0, 0x1e, 0x35, 0x06, 0x04, 0x00, 0x00,
	0xff, 0xff, 0xec, 0x51, 0x2b, 0xa7, 0xf6, 0x00, 0x00, 0x00,
}


//pb_test.go
package pb

import (
	"encoding/json"
	"fmt"
	"github.com/golang/protobuf/proto"
	"testing"
	"time"
)

type JsonAgentData struct {
	SubPlayer            []JsonDownPosition `protobuf:"bytes,1,rep,name=SubPlayer,proto3" json:"s,omitempty"`
	Compelte             int32           `protobuf:"varint,2,opt,name=Compelte,proto3" json:"c,omitempty"`
	Level                int32           `protobuf:"varint,3,opt,name=Level,proto3" json:"l,omitempty"`
	PlayerID             int64           `protobuf:"varint,4,opt,name=PlayerID,proto3" json:"p,omitempty"`
}

type JsonDownPosition struct {
	PlayerID             int64    `protobuf:"varint,1,opt,name=PlayerID,proto3" json:"p,omitempty"`
	Pos                  int32    `protobuf:"varint,2,opt,name=Pos,proto3" json:"l,omitempty"`
}

func TestJson(t *testing.T) {
	fmt.Printf("start:%v\n", time.Now().UnixNano())
	playerID := int64(181676179428737024)
	target := JsonAgentData{
		PlayerID:playerID,
		Level: 10,
		SubPlayer: []JsonDownPosition{},
	}

	for i:=1; i<=11; i++ {
		playerID =playerID + int64(i)
		s := JsonDownPosition{
			PlayerID: playerID,
			Pos: int32(i),
		}
		target.SubPlayer = append(target.SubPlayer, s)
	}

	data, err := json.Marshal(target)
	if err != nil {
		fmt.Printf("err:%v\n", err)
		return
	}
	fmt.Printf("len:%v\n", len(data))
	fmt.Printf("data:%v\n", string(data))

	var marData JsonAgentData
	err = json.Unmarshal(data, &marData)
	if err != nil {
		fmt.Printf("err:%v\n", err)
		return
	}
	fmt.Printf("%+v\n", marData)
	fmt.Printf("end:%v\n", time.Now().UnixNano())
}

func TestPb(t *testing.T) {
	fmt.Printf("start:%v\n", time.Now().UnixNano())

	playerID := int64(181676179428737024)
	target := AgentData{
		PlayerID:playerID,
		Level: 10,
		SubPlayer: []*DownPosition{},
	}

	for i:=1; i<=11; i++ {
		playerID =playerID + int64(i)
		s := &DownPosition{
			PlayerID: playerID,
			Pos: int32(i),
		}
		target.SubPlayer = append(target.SubPlayer, s)
	}

	data, err := proto.Marshal(&target)
	if err != nil {
		fmt.Printf("err:%v\n", err)
		return
	}
	fmt.Printf("len:%v\n", len(data))

	var marData AgentData
	err = proto.Unmarshal(data, &marData)
	if err != nil {
		fmt.Printf("err:%v\n", err)
		return
	}
	fmt.Printf("%+v\n", marData)
	fmt.Printf("end:%v\n", time.Now().UnixNano())
}

1.go test -run=TestJson
start:1560528725799255700
len:380
data:{"s":[{"p":181676179428737025,"l":1},{"p":181676179428737027,"l":2},{"p":181676179428737030,"l":3},{"p":181676179428737034,"l":4},{"p":181676179428737039,"l":5},{"p":181676179428737045,"l":6},{"p":181676179428737052,"l":7},{"p":181676179428
737060,"l":8},{"p":181676179428737069,"l":9},{"p":181676179428737079,"l":10},{"p":181676179428737090,"l":11}],"l":10,"p":181676179428737024}
{SubPlayer:[{PlayerID:181676179428737025 Pos:1} {PlayerID:181676179428737027 Pos:2} {PlayerID:181676179428737030 Pos:3} {PlayerID:181676179428737034 Pos:4} {PlayerID:181676179428737039 Pos:5} {PlayerID:181676179428737045 Pos:6} {PlayerID:1816761
79428737052 Pos:7} {PlayerID:181676179428737060 Pos:8} {PlayerID:181676179428737069 Pos:9} {PlayerID:181676179428737079 Pos:10} {PlayerID:181676179428737090 Pos:11}] Compelte:0 Level:10 PlayerID:181676179428737024}
end:1560528725801249200

2.go test -run=TestPb
start:1560528776984615200
len:166
{SubPlayer:[PlayerID:181676179428737025 Pos:1  PlayerID:181676179428737027 Pos:2  PlayerID:181676179428737030 Pos:3  PlayerID:181676179428737034 Pos:4  PlayerID:181676179428737039 Pos:5  PlayerID:181676179428737045 Pos:6  PlayerID:18167617942873
7052 Pos:7  PlayerID:181676179428737060 Pos:8  PlayerID:181676179428737069 Pos:9  PlayerID:181676179428737079 Pos:10  PlayerID:181676179428737090 Pos:11 ] Compelte:0 Level:10 PlayerID:181676179428737024 Data:[] XXX_NoUnkeyedLiteral:{} XXX_unreco
gnized:[] XXX_sizecache:0}
end:1560528776988559700
3.结果          大小(字节)                           编解码时间

  json            380

  pb              166

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值