4. 性能压测
4.1. 测试环境
CPU : Intel Core i5-7500 3.4GHz 3.4GHz
Momey : 16GB
OS : WINDOWS 10
JAVA IDE : Eclipse 2018-12
4.2. 测试案例
压测对象:okjson v0.0.8.0、fastjson v1.2.56。
压测JSON解析器性能。JSON文本数据映射到实体类各属性里去,交替各压5轮,每轮100万次。
压测JSON生成器性能。由实体类生成JSON文本,交替各压5轮,每轮200万次。
JSON文件press.json
{
"str1" : "str1" ,
"int1" : 1234 ,
"double1" : 1.234 ,
"boolean1" : true ,
"press2" : {
"byte2" : 2 ,
"short2" : 23 ,
"long2" : 23456789 ,
"float2" : 2.345
}
}
实体类PressDataClass.java
package xyz.calvinwilliams.test_jsonparser;
public class PressDataClass {
private String str1 ;
private int int1 ;
private Double double1 ;
private boolean boolean1 ;
private String null1 ;
public PressDataClass2 press2 ;
public String getStr1() {
return str1;
}
public void setStr1(String str1) {
this.str1 = str1;
}
public int getInt1() {
return int1;
}
public void setInt1(int int1) {
this.int1 = int1;
}
public Double getDouble1() {
return double1;
}
public void setDouble1(Double double1) {
this.double1 = double1;
}
public boolean isBoolean1() {
return boolean1;
}
public void setBoolean1(boolean boolean1) {
this.boolean1 = boolean1;
}
public PressDataClass2 getPress2() {
return press2;
}
public void setPress2(PressDataClass2 press2) {
this.press2 = press2;
}
public String getNull1() {
return null1;
}
public void setNull1(String null1) {
this.null1 = null1;
}
}
实体类PressDataClass2.java
package xyz.calvinwilliams.test_jsonparser;
public class PressDataClass2 {
private byte byte2 ;
private short short2 ;
private Long long2 ;
private float float2 ;
public byte getByte2() {
return byte2;
}
public void setByte2(byte byte2) {
this.byte2 = byte2;
}
public short getShort2() {
return short2;
}
public void setShort2(short short2) {
this.short2 = short2;
}
public Long getLong2() {
return long2;
}
public void setLong2(Long long2) {
this.long2 = long2;
}
public float getFloat2() {
return float2;
}
public void setFloat2(float float2) {
this.float2 = float2;
}
}
4.3. fastjson压测代码
fastjson解析器压测代码PressFastJsonParser.java
package xyz.calvinwilliams.test_jsonparser;
import java.io.File;
import java.io.FileInputStream;
import com.alibaba.fastjson.*;
public class PressFastJsonParser {
public static void main(String[] args) {
File file = new File( "press.json" ) ;
Long fileSize = file.length() ;
byte[] json = new byte[fileSize.intValue()] ;
try {
FileInputStream in = new FileInputStream(file);
in.read(json);
in.close();
} catch (Exception e) {
e.printStackTrace();
return;
}
String jsonString = new String(json) ;
long l , count = 1000000 ;
long beginMillisSecondstamp = System.currentTimeMillis() ;
for( l = 0 ; l < count ; l++ ) {
PressDataClass obj = JSON.parseObject(jsonString, new TypeReference<PressDataClass>() {}) ;
if( obj == null ) {
System.out.println( "JSON.stringToObject failed" );
return;
}
else if( l == 0 ){
System.out.println( "JSON.stringToObject ok" );
System.out.println( "------------------------------ dump PressDataClass" );
System.out.println( "DataClass.str1["+obj.getStr1()+"]" );
System.out.println( "PressDataClass.int1["+obj.getInt1()+"]" );
System.out.println( "PressDataClass.Double1["+obj.getDouble1()+"]" );
System.out.println( "PressDataClass.boolean1["+obj.isBoolean1()+"]" );
System.out.println( "------------------------------ dump PressDataClass.press2" );
if( obj.press2 != null ) {
System.out.println( "PressDataClass.branch2.byte2["+obj.press2.getByte2()+"]" );
System.out.println( "PressDataClass.branch2.short2["+obj.press2.getShort2()+"]" );
System.out.println( "PressDataClass.branch2.Long2["+obj.press2.getLong2()+"]" );
System.out.println( "PressDataClass.branch2.float2["+obj.press2.getFloat2()+"]" );
}
}
}
long endMillisSecondstamp = System.currentTimeMillis() ;
double elpaseSecond = (endMillisSecondstamp-beginMillisSecondstamp)/1000.0 ;
System.out.println( "count["+count+"] elapse["+elpaseSecond+"]s" );
double countPerSecond = count / elpaseSecond ;
System.out.println( "count per second["+countPerSecond+"]" );
return;
}
}
fastjson生成器压测代码PressFastJsonGenerator.java
package xyz.calvinwilliams.test_jsonparser;
import java.io.File;
import java.io.FileInputStream;
import com.alibaba.fastjson.*;
public class PressFastJsonGenerator {
public static void main(String[] args) {
PressDataClass object = new PressDataClass() ;
object.setStr1("str1");
object.setInt1(1234);
object.setDouble1(1.234);
object.setBoolean1(true);
object.setNull1(null);
object.press2 = new PressDataClass2() ;
object.press2.setByte2((byte)2);
object.press2.setShort2((short)23);
object.press2.setLong2(23456789L);
object.press2.setFloat2(2.345f);
System.out.println( "------------------------------ dump PressDataClass" );
System.out.println( "DataClass.str1["+object.getStr1()+"]" );
System.out.println( "PressDataClass.int1["+object.getInt1()+"]" );
System.out.println( "PressDataClass.Double1["+object.getDouble1()+"]" );
System.out.println( "PressDataClass.boolean1["+object.isBoolean1()+"]" );
System.out.println( "PressDataClass.null1["+object.getNull1()+"]" );
System.out.println( "------------------------------ dump PressDataClass.press2" );
if( object.press2 != null ) {
System.out.println( "PressDataClass.branch2.byte2["+object.press2.getByte2()+"]" );
System.out.println( "PressDataClass.branch2.short2["+object.press2.getShort2()+"]" );
System.out.println( "PressDataClass.branch2.Long2["+object.press2.getLong2()+"]" );
System.out.println( "PressDataClass.branch2.float2["+object.press2.getFloat2()+"]" );
}
long l , count = 5000000 ;
long beginMillisSecondstamp = System.currentTimeMillis() ;
for( l = 0 ; l < count ; l++ ) {
String jsonString = JSON.toJSONString( object ) ;
if( jsonString == null ) {
System.out.println( "JSON.toJSONString failed" );
return;
}
else if( l == count-1 ){
System.out.println( "JSON.toJSONString ok" );
System.out.println( jsonString );
}
}
long endMillisSecondstamp = System.currentTimeMillis() ;
double elpaseSecond = (endMillisSecondstamp-beginMillisSecondstamp)/1000.0 ;
System.out.println( "count["+count+"] elapse["+elpaseSecond+"]s" );
double countPerSecond = count / elpaseSecond ;
System.out.println( "count per second["+countPerSecond+"]" );
return;
}
}
4.4. okjson压测代码
okjson解析器压测代码PressOkJsonParser.java
package xyz.calvinwilliams.test_jsonparser;
import java.io.File;
import java.io.FileInputStream;
import xyz.calvinwilliams.okjson.*;
import xyz.calvinwilliams.test_jsonparser.PressDataClass;
public class PressOkJsonParser {
public static void main(String[] args) {
File file = new File( "press.json" ) ;
Long fileSize = file.length() ;
byte[] json = new byte[fileSize.intValue()] ;
try {
FileInputStream in = new FileInputStream(file);
in.read(json);
in.close();
} catch (Exception e) {
e.printStackTrace();
return;
}
String jsonString = new String(json) ;
long l , count = 1000000 ;
long beginMillisSecondstamp = System.currentTimeMillis() ;
for( l = 0 ; l < count ; l++ ) {
PressDataClass object = OKJSON.stringToObject( jsonString, PressDataClass.class, OKJSON.OPTIONS_DIRECT_ACCESS_PROPERTY_ENABLE ) ;
if( object == null ) {
System.out.println( "okjson.stringToObject failed["+OKJSON.getErrorCode()+"]" );
return;
} else if( l == 0 ){
System.out.println( "okjson.stringToObject ok" );
System.out.println( "------------------------------ dump PressDataClass" );
System.out.println( "DataClass.str1["+object.getStr1()+"]" );
System.out.println( "PressDataClass.int1["+object.getInt1()+"]" );
System.out.println( "PressDataClass.Double1["+object.getDouble1()+"]" );
System.out.println( "PressDataClass.boolean1["+object.isBoolean1()+"]" );
System.out.println( "------------------------------ dump PressDataClass.press2" );
if( object.press2 != null ) {
System.out.println( "PressDataClass.branch2.byte2["+object.press2.getByte2()+"]" );
System.out.println( "PressDataClass.branch2.short2["+object.press2.getShort2()+"]" );
System.out.println( "PressDataClass.branch2.Long2["+object.press2.getLong2()+"]" );
System.out.println( "PressDataClass.branch2.float2["+object.press2.getFloat2()+"]" );
}
}
}
long endMillisSecondstamp = System.currentTimeMillis() ;
double elpaseSecond = (endMillisSecondstamp-beginMillisSecondstamp)/1000.0 ;
System.out.println( "count["+count+"] elapse["+elpaseSecond+"]s" );
double countPerSecond = count / elpaseSecond ;
System.out.println( "count per second["+countPerSecond+"]" );
return;
}
}
okjson生成器压测代码PressOkJsonGenerator.java
package xyz.calvinwilliams.test_jsonparser;
import java.io.File;
import java.io.FileInputStream;
import xyz.calvinwilliams.okjson.OKJSON;
import xyz.calvinwilliams.test_jsonparser.PressDataClass;
public class PressOkJsonGenerator {
public static void main(String[] args) {
PressDataClass object = new PressDataClass() ;
object.setStr1("str1");
object.setInt1(1234);
object.setDouble1(1.234);
object.setBoolean1(true);
object.setNull1(null);
object.press2 = new PressDataClass2() ;
object.press2.setByte2((byte)2);
object.press2.setShort2((short)23);
object.press2.setLong2(23456789L);
object.press2.setFloat2(2.345f);
System.out.println( "------------------------------ dump PressDataClass" );
System.out.println( "DataClass.str1["+object.getStr1()+"]" );
System.out.println( "PressDataClass.int1["+object.getInt1()+"]" );
System.out.println( "PressDataClass.Double1["+object.getDouble1()+"]" );
System.out.println( "PressDataClass.boolean1["+object.isBoolean1()+"]" );
System.out.println( "PressDataClass.null1["+object.getNull1()+"]" );
System.out.println( "------------------------------ dump PressDataClass.press2" );
if( object.press2 != null ) {
System.out.println( "PressDataClass.branch2.byte2["+object.press2.getByte2()+"]" );
System.out.println( "PressDataClass.branch2.short2["+object.press2.getShort2()+"]" );
System.out.println( "PressDataClass.branch2.Long2["+object.press2.getLong2()+"]" );
System.out.println( "PressDataClass.branch2.float2["+object.press2.getFloat2()+"]" );
}
long l , count = 5000000 ;
long beginMillisSecondstamp = System.currentTimeMillis() ;
for( l = 0 ; l < count ; l++ ) {
String jsonString = OKJSON.objectToString( object, 0 ) ;
if( jsonString == null ) {
System.out.println( "okjson.stringToObject failed["+OKJSON.getErrorCode()+"]["+OKJSON.getErrorDesc()+"]" );
return;
} else if( l == count-1 ){
System.out.println( "okjson.stringToObject ok" );
System.out.println( jsonString );
}
}
long endMillisSecondstamp = System.currentTimeMillis() ;
double elpaseSecond = (endMillisSecondstamp-beginMillisSecondstamp)/1000.0 ;
System.out.println( "count["+count+"] elapse["+elpaseSecond+"]s" );
double countPerSecond = count / elpaseSecond ;
System.out.println( "count per second["+countPerSecond+"]" );
return;
}
}
4.5. 测试过程
JSON解析器性能
okjson
count[1000000] elapse[1.446]s
count per second[691562.9322268326]
fastjson
count[1000000] elapse[2.616]s
count per second[382262.996941896]
okjson
count[1000000] elapse[1.429]s
count per second[699790.0629811056]
fastjson
count[1000000] elapse[2.547]s
count per second[392618.767177071]
okjson
count[1000000] elapse[1.42]s
count per second[704225.3521126761]
fastjson
count[1000000] elapse[2.473]s
count per second[404367.1653861707]
okjson
count[1000000] elapse[1.432]s
count per second[698324.0223463688]
fastjson
count[1000000] elapse[2.48]s
count per second[403225.8064516129]
okjson
count[1000000] elapse[1.434]s
count per second[697350.069735007]
fastjson
count[1000000] elapse[2.459]s
count per second[406669.37779585196]
JSON生成器性能
okjson
count[2000000] elapse[1.399]s
count per second[1429592.5661186562]
fastjson
count[2000000] elapse[1.51]s
count per second[1324503.311258278]
okjson
count[2000000] elapse[1.347]s
count per second[1484780.9948032666]
fastjson
count[2000000] elapse[1.507]s
count per second[1327140.0132714002]
okjson
count[2000000] elapse[1.364]s
count per second[1466275.6598240468]
fastjson
count[2000000] elapse[1.403]s
count per second[1425516.7498218103]
okjson
count[2000000] elapse[1.363]s
count per second[1467351.4306676448]
fastjson
count[2000000] elapse[1.512]s
count per second[1322751.3227513228]
okjson
count[2000000] elapse[1.37]s
count per second[1459854.01459854]
fastjson
count[2000000] elapse[1.409]s
count per second[1419446.4158978]
4.6. 测试结果
JSON解析器性能曲线图:
JSON生成器性能曲线图:
说明:
- 在JSON解析/反序列化处理性能上,okjson比fastjson快了近一倍(75%)。
- 在JSON生成/序列化处理性能上,okjson比fastjson快了少许(7%)
其它说明:
- fastjson静态类名为JSON取名不好,容易和其它JSON库冲突,或许温少就是这么霸气。okjson静态类名为OKJSON,比较低调 :)
- 实体类中加了很多setter和getter是为了fastjson,okjson并不需要。okjson甚至连实体类构造方法都没有要求必须有,作为通用框架要兼容各种各样的场景。
当前内容版权归 calvinwilliams 或其关联方所有,如需对内容或内容相关联开源项目进行关注与资助,请访问 calvinwilliams .