如何检测特殊字符(如何快速检测是否为空白字符)
如何检测特殊字符(如何快速检测是否为空白字符)使用阿里云x64当前代计算型4核8G服务器,CPU型号 Intel Xeon(Ice Lake) Platinum 8369B通过预计算一个常量的long,然后做bitAnd判断。fastjson2 ( https://github.com/alibaba/fastjson2 )判空用的是这个方法。这个常规办法,用6个并列的or判断。所有的字符检测都需要做6次判断,性能较差。由于空白字符最大的是空格ASCII 32,在方法2的基础上先做一个预先检测,这样就能获得非常好的性能,但当输入的有大量空白字符\b时,就就会面临方法2的问题。fastjson 1.x ( GitHub - alibaba/fastjson: A fast JSON parser/generator for Java. )判空用的是这个方法。这种算法,在JDK 17下性能有较大提升。在大量输入是非空字符时,性能并不出色。
作者:温绍锦(高铁) 阿里云计算平台团队
在Parser场景,包括SQL Parser和JSON Parser,如何更快检测空白字符是一个提升性能的关键点。笔者有多年SQL Parser和JSON Parser的经验,把我所知道的一些检测空白的方法分享给大家。
一、什么是空白字符如果采用json.org的标准,空白字符包括:
JDK的Character提供了isWhiteSpace方法,逻辑不能定制化,不支持上面的'\b'字符判空,但为了性能比较,也加入进来。
这个常规办法,用6个并列的or判断。所有的字符检测都需要做6次判断,性能较差。
由于空白字符最大的是空格ASCII 32,在方法2的基础上先做一个预先检测,这样就能获得非常好的性能,但当输入的有大量空白字符\b时,就就会面临方法2的问题。fastjson 1.x ( GitHub - alibaba/fastjson: A fast JSON parser/generator for Java. )判空用的是这个方法。
这种算法,在JDK 17下性能有较大提升。在大量输入是非空字符时,性能并不出色。
通过预计算一个常量的long,然后做bitAnd判断。
fastjson2 ( https://github.com/alibaba/fastjson2 )判空用的是这个方法。
使用阿里云x64当前代计算型4核8G服务器,CPU型号 Intel Xeon(Ice Lake) Platinum 8369B
使用阿里云ARM当前代计算型4核8G服务器,CPU型号 Ampere Altra / AltraMax
下载Oracle最新的LTS版本Linux JDK
测试代码:
https://github.com/alibaba/fastjson2/tree/main/benchmark/src/main/java/com/alibaba/fastjson2/benchmark
执行测试代码
JDK8 |
JDK11 |
JDK17 | |
方法1 |
1756.884 |
1692.215 |
1770.658 |
方法2 |
1911.820 |
1866.888 |
1903.105 |
方法3 |
3496.629 |
4228.972 |
3956.434 |
方法4 |
2798.679 |
2910.525 |
2876.148 |
方法5 |
3522.462 |
3694.007 |
4474.286 |
- 原始数据
JDK8 |
JDK11 |
JDK17 | |
方法1 |
911.795 |
785.339 |
1269.834 |
方法2 |
789.439 |
833.830 |
842.177 |
方法3 |
2304.419 |
2429.907 |
2146.953 |
方法4 |
880.387 |
1124.967 |
1540.419 |
方法5 |
2363.957 |
2392.123 |
2570.536 |
- 原始数据
综合来看,无论是x64还是aarch64,方法5性能最理想。