开头还是介绍一下群,如果感兴趣polardb ,mongodb ,mysql ,postgresql ,redis 等有问题,有需求都可以加群群内有各大数据库行业大咖,CTO,可以解决你的问题。
本来不想写的但没有刘老师的微信,很想表达感谢所以有了此篇,先说说怎么回事,上图假期后的第一篇文字,在早上6点发出来,8点就不断有同学给我截图,说你写错了。我看了看截图,OMG ,ORACLE 大佬。 我的第一个感觉是,啊,我写错了。我写错了不是很正常吗,错字,计算错误,被DISS。不过这次大佬DISS ,我的好好的看看自己是哪里错了,先自省。然后此间2天不断有各种同学给我私下贴图,我都毛了。
首选写到前面,感谢老虎刘老师,快速的反馈,另外PG的优化器的问题,这个,嗯,您试试MYSQL的可好,我们PG 还没有那么弱鸡,当然和ORACLE 比较吗,什么数据库他不是弱鸡呢 ?重要的是咱们PG免费,免费 ,免费,另外老虎刘老师都关注的数据库,那必然是一个值得关注的数据库,我们POSTGRESQL 配得上
The world's most advanced open source database 的title
再次感谢老虎刘老师也欢迎刘老师加群,给我们普及ORACLE的相关知识!另外群里也有很多您的粉丝哈,都在群里说 老虎刘 牛逼的老师
——————————————————————————————
事情先的说两面这一两天我都做了什么,首先ORACLE 数据库的Merge join 绝对是可以支持非等值的连接,但是POSTGRESQL 嗯,能不能支持这个非等值,或者说,在实际的运行中,能进行非等值的运算使用merge join,这个还是的在验证
1 我怕我记错了
2 我如果错了,我的改正,避免产生错误的信息导向性
在说这个问题前,各位ORACLE 的专家们,容小的禀告几个问题
1 POSTGRESQL 没有和ORACLE 一样的 HINT ,或者说HINT 的使用插件
2 POSTGRESQL 在优化器方面,是粗狂的同时比ORACLE 好的地方是可以调整很多参数,就算和ORACLE相比,我们也是数据库业界的一朵瑰宝。
3 POSTGRESQL 在优化器细节方面 ,实话实说,没法和ORACLE 相比。
此间我赶紧打开了POSTGRESQL 的源代码,中的MERGE JOIN 部分
这没错呀,不行我们还的开始试验,看看是不是新的版本有了这个功能,(实际上我没有听说,但怕漏掉,采用了PG14.7)
测试比较简陋,但为了速度,也只能这样了,我采用了PG 通用的测试库dvdrental .下面就是PG 比很多数据库,包含ORACLE 都强悍的地方了,可以调整各种查询方式的开关设置。
这里我们暂时不调节任何的开关,按照默认的方式来
dvdrental=# explain analyze select *
from customer as c
left join payment as p on c.customer_id >= p.customer_id;
QUERY PLAN
Nested Loop Left Join (cost=0.29..80820.42 rows=2914335 width=96) (actual time=0.033..1082.925 rows=4417156 loops=1)
-> Seq Scan on customer c (cost=0.00..14.99 rows=599 width=70) (actual time=0.011..0.210 rows=599 loops=1)
-> Index Scan using idx_customer_id on payment p (cost=0.29..86.25 rows=4865 width=26) (actual time=0.004..0.918 rows=7374 loops=599)
Index Cond: (customer_id <= c.customer_id)
Planning Time: 0.179 ms
Execution Time: 1199.960 ms
(6 rows)
走了Nested loop 的方式来进行两个表的联合查询, 下面我们变换了查询的方式,变为等值查询,可以看到我们使用了merge join 的方式来进行了两个表的关联查询
Merge Left Join (cost=0.56..926.88 rows=14596 width=96) (actual time=0.060..4.970 rows=14596 loops=1)
Merge Cond: (c.customer_id = p.customer_id)
-> Index Scan using customer_pkey on customer c (cost=0.28..37.63 rows=599 width=70) (actual time=0.006..0.095 rows=599 loops=1)
-> Index Scan using idx_customer_id on payment p (cost=0.29..705.31 rows=14596 width=26) (actual time=0.047..2.348 rows=14596 loops=1)
Planning Time: 0.465 ms
Execution Time: 5.425 ms
那么有没有其他的可能呢,因为测试的表,或索引,或语句的因素,导致如上的结果有问题呢,我们再次在POSTGRESQL 将我们的查询分析器的一些开关关闭。
在我们关闭了一部分可能干扰结果的设置后,我们再次进行查询,见下图,因为无法在非等值的情况下,使用mergejoin PG 在关闭了 netloop的情况下,还是无可奈何的走了 nestloop 。当然这也是PG的一个特点,最终你们都的听我的。
这里总结POSTGRESQL 的MERGE JOIN
1 Merge join 适合大型数据集,基于MERGE JOIN 对输入单次扫描,可以快速的处理大型的数据集合。
2 进行连接的表进行连接的部分要进行排序
3 只能处理等值连接,仅仅等两个表的连接符号为等号时才可以进行merge join (我们期待PG 未来能和ORACLE 一样不等值也能进行MJ)
4 需要有足够的内存,需要在RAM中保留输入的表的副本,来在内存中进行连接操作
5 可以进行并行化的加速,多核心的CPU 可以在MERGE JOIN 中提高查询的速度
写到最后再次感谢老虎刘,刘老师,比心 !!!
另ORACLE 在国内的形势很艰巨,这也是人尽皆知的,新型的数据库一个塞一个,更多的新概念,当然也有缺点,如同盖老师5年前了提出的概念,数据库百花齐放,当年听起来好像就是天方夜谭,现在恍如隔世,当今的数据库世界太灿烂了。
另附:昨天还听了,盖老师和韩老师的 “锵锵三人行”, 等待国产的TPCC,加油!!!