给段json
让你解析json ,你咋弹了个计算器?
fastjson: 你别管,你就说快不快吧
ps:现在fastjson2出了,已经重构了,安全问题已经得到很好的改善
哈哈哈,我来回答这个问题!因为我实在是对这两个库太熟悉了。
1、你写个bean,然后属性里分别有包含_(下划线开头、#开头)之类的属性,序列化为json时,出现属性丢失,那么自然你也无法反序列化回来,据说最新的1.2.14已经改正了这个bug(我没测试不做评价);
2、翻阅fastjson的源码,你会发现有很多写死的代码,比如:针对spring之类的框架的各种处理,都是用classload判断是否存在这种类名
fastjson/SerializeConfig.java at master · alibaba/fastjson · GitHub
;那么这是什么意思呢?意思就是如果你用spring的那种思想,自己写了个类似的功能,因为你这个项目里没有spring的那个类,那么用起来就有一堆bug;当然不仅限于这些,还有很多,比如ASM字节码织入部分
fastjson/ASMSerializerFactory.java at master · alibaba/fastjson · GitHub
(温少的ASM方面水平是个半吊子),看源码的话,能发现的缺点数不胜数。
3、其解析json主要是用的String类substring这个方法
fastjson/JSONScanner.java at master · alibaba/fastjson · GitHub
,所以解析起来非常“快”,因为申请内存次数很少。但是因为jdk1.7之前substring的实现并没有new一个新对象,在使用的时候,如果解析的json非常多,稍不注意就会出现内存泄漏(比如一个40K的json,你在对象里引用了里边的一个key,即使这个key只有2字节,也会导致这40K的json无法被垃圾回收器回收),这也是“快”带来的负面效果。而且这还不算,在jdk1.7以上版本对string的substring方法做了改写,改成了重新new一个string的方式,于是这个“快”的优势也不存在了。
总结:fastjson就是一个代码质量较差的国产类库,用很多投机取巧的的做法去实现所谓的“快”,而失去了原本应该兼容的java特性,对json标准遵循也不严格,自然很难在国际上流行。
感谢htyleo更正,我改一下。
------------我是分割线-------------
fastjson作者在看到本文后,今天告诉我已经改正了问题1,给
温高铁
先生点赞。
json从发明到现在非常流行,并不是因为json快的原因(比json快且小巧的格式和类库一大把),而是因为json和web结合的时候更易于使用,对开发人员易于理解。很多人拿fastjson和jackson比,就像拿非智能机和iphone比待机时间,其功能性不一样,jackson的很多功能fastjson并没有实现,所以这种对比也不客观。fastjson之所以没在国际上流行起来,最主要的原因应该是开发者的思路全放到“快”上去了,而偏离了“标准”及功能性,质量也不够好,有点“舍本逐末”的味道。
当然在目前的环境下,国产软件能踏实的心态做好开源的不多,fastjson团队能这么快的反馈并修正问题,这种精神还是值得称赞的。希望国内的技术从业者能更重视“技术的原始需求”。
截图取自fastjson在github上的文档
alibaba/fastjson
。
多说一句,就凭这个对待友商的态度,个人就不推荐使用它,更何况各方权衡之下,jackson比他优秀太多。快不是唯一的需求。
这里说几个问题:
读了1.2.21版代码,fastjson在成serializer时,会对一些简单的类直接生成字节码,这样类似于优化编译,确实可以快那么一点,但具体实现上,生成的代码漏掉了很多 SerializerFeature,或者可以说根本没有根据类注解 @JSONType 中定义的去生成字节码。代码行为前后不一致问题,这个黑点洗不掉的。
代码中有很多写死的实现,导致扩展性不高,这点别的回答已经有涉及,但是我这里多说一点,因为工作关系,需要涉及阿里系的各种开闭源库,为了调试也反编译过阿里的闭源代码,这种完全不考虑扩展性的写法在阿里系的代码里边随处可见。或许可以解释说阿里内部使用不需要这种扩展性,但是作为开源库,想要别人用,要面对各种情况处理各种异常,阿里系的这种代码显然力不从心的。
个人来讲,不会在任何项目中首先考虑使用阿里系技术。
利益相关,阿里系企业员工。