Java 在我的例子中,为什么协议缓冲区的性能比JSON差?

Java 在我的例子中,为什么协议缓冲区的性能比JSON差?,java,json,protocol-buffers,Java,Json,Protocol Buffers,我正在协议缓冲区和json之间进行测试,但我发现协议缓冲区的性能超出了我的预期。我想知道我的http请求是否太复杂,或者协议缓冲区是否不适合我的情况。这是我的http请求: { “LogId”:“ABC165416515166165484165164132”, “ci_come”:“uvInYKaMbhcyBm4p”, “ci_cme”:“GWPMzgSwKzEZ5Mmz”, “ci_me”:“GQHVRASDTEKSGIHM18QZAJCVH21BBAQ0TKNIXBQNKKAPQBSZG35

我正在协议缓冲区和json之间进行测试,但我发现协议缓冲区的性能超出了我的预期。我想知道我的http请求是否太复杂,或者协议缓冲区是否不适合我的情况。这是我的http请求:

{
“LogId”:“ABC165416515166165484165164132”,
“ci_come”:“uvInYKaMbhcyBm4p”,
“ci_cme”:“GWPMzgSwKzEZ5Mmz”,
“ci_me”:“GQHVRASDTEKSGIHM18QZAJCVH21BBAQ0TKNIXBQNKKAPQBSZG35CDG6USAXWOXXIEY9ANKBSN”,
“ci_pi”:“U6DPU0828Q0NNP5JRGVcmgn41POXFPLZHWU6FDBORFSUJZSKD0HKTCQAXBGAOUYCCKGTZDS9ROJSK”,
“th_logic”:“IUPPORTxr_17_iIT_yis=[lthyoyy.gitg.warmh;@6icy855 VXRSIONCRX=1 uiyRr=msm8953 uiOTLOyrxR=unknown uPx=ujij Ir=N2G47H TIMx=1541178617000 iRyNr=gitrI TyG=iuilr HyRrWyRx=QYYYYYL=1743iC101955 SUPPORTxr_yis”=[Lhug.hxng.warmh;@5ic26y CPU_yi=yrm17-v8y是_rxuiggyilx=fylsx RyrIO=unknown mynufycutrxr=gitrI是_xMULyTOR=fylsx SUPPORTxr_32_iIT_yis=(2)中国农村基层政府组织。中国农村基层政府;中国农村农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村基层政府;中国农村政府;中国农村基层政府:TXXXXGGGGs=TXX=未知的X X X X=中国农村学校,中国政府,中国政府,中国政府,中国政府,中国农村的X X-X-X-X-X-X-X-X-X-X-X-X X-T=T=T=T=T=T=T=T=T=T=T-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-X-选项:rivirx Y Y Y Y x Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y x W.vixw.FXW.vixw.VXX x x x x x x x x x x x x x x x x x x x x x x.FCCXX x x x x x x x x x x x x x x x x.ViX x x x x x x x x x x x x x.ViXX x x x x x x x x x x x x x x x x x x x x x x x x.vixw.vixw.vixw.vixw.x x x ooxx8krituil“,
“th_理想”:“TqpXdC5NQF”,
“THU sth”:“YTvmyusuprqzhaqlgrdvxp0g8nlwdezbc0ufrcyrqv09ckpbuacesmfiqxhp2g2duvmnzmv20ibbqcuakuakpikvs9mvr9ymxd5yyahybsdowetqdkjautbs115rqdghe2qdwmcrnzf9f4wf5sjsflmxrozprr”,
“THU err”:“StGMzqIW1YGg44GC”,
“th_代码”:“ZRHWEAVMVVLNPTUZCCO0J62BFJL6SJNB8JXNNG645FQOMLXA5CEKOWH67AYKK0FNM3VKMPXABDLWCWAYVUJUVCH1”,
“th_需求”:“ZWZXPUr6O4jYrXjLXlXskem7jHQ6D”,
“th_索引”:“6546546546”,
“日志”:“3GT8V7LMXUMLVHPZCVUYCQL8ZVWADFDEZWN7GXOHBZF9QUOZFTL2WWFRPMOX2V8ZFJBOQIIG4DXJF0X1VWGKHHHVNMABXCO5JDWVE33TGI0YTJO14UYENEZYDOER51”,
“顺序”:“T28XGCx1O3LCGa98lAtWc33”,
“消息”:“崩溃”,
“时间”:“2019-11-11 18:23:00”,
“ci_vi”:“RCgdDu5874sJohjEVy7i72Kcp98rCOJvl”,
“t_mNo”:“1.9”,
“t_tNo”:“GXK9VB3ZBLP2HPYTQZTXMZX43WAETZMA3CWFFXTPSDZFGAAIUG5MBx73W4WQVWNL65BEOW3FD7WEXNDZM3EILP4JODTHZQAV5G574FPFK”,
“t_fd”:“K58XS1EYKTVDSBRBRMWFPjMDB6TFBNGAOLANMDUZXO2 UREBVTD8F”,
“t_pd”:“jWl7CTWdmgVFZxA”,
“t_oer”:“HHoLyXNYxKHqZgpev9vi”,
“t_ar”:“J6m4X9ATlADGaKUzi1eb”,
“t_sr”:“daP”,
“t_sd”:“AGXPBAORA95B9PM4196BQALSVN9J9”,
“t_sn”:“1Ai4lFVObo0MymeJ894m0jItjiwhcD”,
“t_dd”:“zLuh1p1G”,
《泰晤士报》:“2019-11-11 18:22:58”
} 
这是我的原始文件:

消息Scada{
TechInfo tInfo=1;
字符串时间=2;
字符串消息=3;
思维=4;
} 
信息技术信息{
字符串mNo=1;
字符串tNo=2;
字符串fd=3;
串pd=4;
字符串oer=5;
字符串ar=6;
Ci-cd=7;
字符串sr=8;
字符串sd=9;
串sn=10;
字符串dd=11;
} 
消息Ci{
字符串pi=1;
字符串vi=2;
字符串me=3;
字符串cme=4;
字符串=5;
} 
信息思维{
字符串逻辑=1;
弦理想=2;
字符串sth=3;
字符串错误=4;
字符串代码=5;
字符串req=6;
字符串索引=7;
字符串log=8;
字符串顺序=9;
} 
我使用protocol buffers parseFrom()方法来反序列化请求:

公共静态Scada pbDeSerialize(字节[]pbBytes)引发InvalidProtocolBufferException{
Scada=ScadaObj.Scada.parseFrom(PB字节);
返回scada;
} 
我使用json工具来反序列化请求:

公共静态PbScadaJsonObj jsonDeserialize(字节[]jsonBytes){
String str=新字符串(jsonBytes,utf8Charset);
返回JsonUtil.deserialize(str,PbScadaJsonObj.class);
} 
公共静态T反序列化(字符串json,类clazz){
返回JSON.parseObject(JSON,clazz);
} 
我使用jmeter测试这两种方法。测试由一个线程和100个线程组成。一条请求消息大约3KB。Json ProtoBuf(PB)反序列化消息以1024MB堆大小进行测试。每次执行之前,我总是添加一个随机数,使消息彼此不同。我的机器是2C4G

+---------------------+----------+------+
| 100k loops 1 thread | FastJson | PB   |
+---------------------+----------+------+
| TIME(s)             | 360      | 309  |
+---------------------+----------+------+
| CPU(%)              | 104      | 99.8 |
+---------------------+----------+------+
| MEM(%)              | 7.2      | 6.6  |
+---------------------+----------+------+


从测试中,我看不出协议缓冲区的改进只增加了50/s的TPS,就消耗了更多的内存。有人能为我解释一下吗?或者有人做过类似这样的测试吗?

比较是不公平的。你的Protobuf定义是嵌套的,而JSON定义是扁平的。如果你想做一个公平的比较,使JSON嵌套或使Protobuf平坦:

使JSON嵌套:

{
 "tInfo" : {"mNo" : "xxxx", "tNo" : "xxxx", "other" : "fields"},
 "time" : "2019-11-11 18:23:00",
 "message" : "Crash",
 "thought" : {"logic" : "xxx", "other" : "fields"}
} 

比较不公平。您的Protobuf定义是嵌套的,而JSON定义是平面的。如果要进行公平比较,请将JSON嵌套或将Protobuf平面化:

使JSON嵌套:

{
 "tInfo" : {"mNo" : "xxxx", "tNo" : "xxxx", "other" : "fields"},
 "time" : "2019-11-11 18:23:00",
 "message" : "Crash",
 "thought" : {"logic" : "xxx", "other" : "fields"}
} 

这是非常简单的JSON,字符串对您的好处最小(字符串基本上就是一个字符串。现在,一个数字……在PB和JSON中更容易读取(并且花费的字节要少得多).Thx用于您的回答。我无法理解您的观点。Pb和Json之间的请求和定义完全相同。我知道字符串消耗的内存多于数字。但我仍然想知道为什么Pb在多线程情况下比Json消耗的内存如此之多。这是非常简单的Json,字符串对您的好处最小(字符串基本上就是一个字符串。现在,一个数字……在PB和JSON中更容易读取(而且花费的字节要少得多).Thx表示您的回答。我无法理解您的观点。Pb和Json之间的请求和定义完全相同。我知道字符串消耗的内存超过数字。但我仍然想知道为什么Pb在多线程情况下比Json消耗的内存多。Thx表示您的回答f