千家信息网

Oracle 和 MySQL 的 JDBC 到底有多慢?

发表于:2024-11-22 作者:千家信息网编辑
千家信息网最后更新 2024年11月22日,经常听人说,数据库的IO性能不佳,但说归说,并没有感性认识。我们现在就来实际测试一下,常用的Oracle和MySQL的JDBC读取性能如何。之所以测试JDBC,是因为大部分应用是JAVA写的,也就只能
千家信息网最后更新 2024年11月22日Oracle 和 MySQL 的 JDBC 到底有多慢?

经常听人说,数据库的IO性能不佳,但说归说,并没有感性认识。我们现在就来实际测试一下,常用的Oracle和MySQL的JDBC读取性能如何。

之所以测试JDBC,是因为大部分应用是JAVA写的,也就只能用JDBC来访问数据。这里仅测试用JDBC读出数据,并产生成Java的记录对象(毕竟到了这一步才能在应用中使用),不作任何计算。

1. 数据来源

使用TPCH生成的数据,选用其中的customer表来做测试,数据记录为3000万行,8个字段。它生成的原始文本文件名为customer.tbl,文件大小为4.9G。利用数据库提供的数据导入工具将此文件数据导入到Oracle和MySQL的数据表中。

2. 测试环境

在一台Intel服务器上完成测试,2个Intel2670 CPU,主频2.6G,共16核,内存64G。数据库表数据及文本文件均存储在同一块SSD硬盘上。

所有测试均在服务器本机上完成,没有消耗网络传输时间。

3. 数据库读数测试

通过Oracle提供的JDBC接口,用SQL语句执行数据读取。

Java写起来麻烦,用SPL脚本执行测试:


A
1=now()/记录时间
2=connect("oracle")/连接数据
3=A2.cursor("select * from customer")/生成取数游标
4for A3,10000/循环取数,每次10000条
5=A2.close()/关闭连接
6=interval@s(A1,now())/计算时长

MySQL的测试代码类似,不再赘述。

测试结果(时间单位:秒)


第一次第二次每秒行数
Oracle293281106K
MySQL51838179K

第二次可能由于操作系统有了硬盘缓存,所以更快。因为我们主要是为了测试JDBC的读取时间,所以就以第二次为准,减少数据库本身从硬盘读数的影响。每秒读出行数也是按第二次时间来计算的,也就是说,Oracle每秒能读出10万行多数据,MySQL大概接近8万行。当然这个值和表的字段数及类型都有关(customer表有8个字段),只是一种参考。

4. 文本文件对比

只从上面的数据量还没有太多感性认识,我们再读一下文本文件来对比。办法是一样的,从文件中读出数据,并解析出记录,不作任何计算。

编写如下SPL脚本执行测试:


A
1=now()/记录时间
2=file("/home/sjr/tbl/customer.tbl")/产生文件对象
3=A2.cursor(;,"|")/生成取数游标,分隔符是|
4for A3,10000/循环取数,每次10000条
5=interval@s(A1,now())/计算时长

测试结果是42秒!

这意味着,读取文本要比读取Oracle快281/42=6.69倍,比MySQL要快381/42=9.07倍!

我们知道,文本解析是个非常麻烦的事情,但即使这样,从文本文件读取数据还是远远快于从数据库中读数。Oracle和MySQL的IO实在是太慢了!

5. 二进制方式

我们进一步再看使用二进制方式的存储格式的读取性能,并和文本比对。

为了对比明显,这次换一个更大的表,用TPCH中的orders表,有3亿行数据,9个字段。

文本读取的代码和上面类似,读取时间测试为438秒。

然后,我们将这个文本文件转换成SPL组表,再写代码测试:


A
1=now()/记录时间
2=file("/home/sjr/ctx/orders.ctx").create()/产生组表对象
3=A2.cursor()/生成取数游标
4for A3,10000/循环取数,每次10000条
5=interval@s(A1,now())/计算时长

测试结果是164秒,大概仅仅是文本读取的三分之一。

这是情理之中的事情,因为二进制数据不再需要解析,可以直接产生对象,计算量少了很多,因而要更快。

需要说明的是,组表文件虽然采用列存格式,但在这里读出了所有列,并没有比文本少取任何内容,没有占列存的便宜。事实上,因为读所有列,使用列存还会吃点亏,如果采用SPL集文件(一种行存格式)还会更快。

6. 并行提速

从文件中取数还很容易实现并行,文本和组表都容易写出并行程序。还是用上面的orders表为例来测试,使用4线程取数。

文本取数代码:


ABC
1>n=4/n是并行数=now()
2=file("/home/sjr/tpch_2_17_0/tbls/orders.tbl")
3fork to(n)=A2.cursor(;A3:n, "|")多线程产生游标,每个游标只取4段中的一段
4
for B3, 10000
5=interval@s(C1,now())

组表取数代码:


ABC
1>n=4/n是并行数=now()
2=file("/home/sjr/ctx/orders.ctx").create()
3fork to(n)=A2.cursor(;;A3:n)多线程产生游标,每个游标只取4段中的一段
4
for B3, 10000
5=interval@s(C1,now())

用SPL很容易实现数据分段和并行计算。

测试结果为:

文本 119秒

组表 43秒

与串行相比,接近了线性提升,将CPU的多核充分利用起来了。

数据库中的数据则不容易简单地实施分段并行,需要用WHERE条件去拼,结果很难说清到底是并行不力还是WHERE执行损失太多,测试结果的参考意义就打折扣了,这里就不再做了。

7. 结论

数据库(Oracle和MySQL)的JDBC性能非常非常差!比文本文件还要差5倍以上。而采用二进制数据时,会比文本再提高3倍的读取性能。也就是说,合理格式的二进制文件会比数据库有15倍以上的优势。再考虑到并行因素,比数据库快出几十上百倍也是完全可能的。

在关注性能且数据量较大时,千万不要把数据读出数据库计算!

如果实在需要读出后再计算(有时SQL很难写出复杂的过程计算),就不要再用数据库存储了(大数据都是历史,基本也不再改了,可以事先读出),用文本都比数据库强,用二进制当然更好(推荐使用SPL组表,哈哈)。切不要把时间浪费在读数这种非计算任务上了。


数据 测试 文本 文件 数据库 时间 游标 二进制 性能 结果 代码 生成 字段 对象 格式 时长 更快 硬盘 线程 读数 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 研发所说的软件开发是啥意思 成睿软件登录服务器返回数据错误 软件开发餐饮行业 打造一个网络安全宣传周 网络安全排行通用软件公司 异构数据库迁移 网络安全教育感受150字 圣猫网络技术服务有限公司 在校大专网络技术该拿什么证 联想服务器通过管理口安装系统 网络安全问题举报电话 监控存储服务器搭建 软件开发论文10000字 服务器无法响应和下载资源出错 计算机网络技术大专排名 数据库等相关技术概念 崇明区营销软件开发服务保障 网络安全的应用场景概念 手机提示无法连接到服务器啥意思 全市网络安全等级培训 华荣网络技术有限公司怎么样 软件开发过程和成果 夜饮网络技术学院论坛 国家网络安全有什么重要性 服务器托管 武汉 网络安全美国深造 留言代码软件开发 义乌制造软件开发流程 服务器配图 xbox无法连接服务器怎么办
0