MariaDB 由 MySQL 的原创人员开发,并被维基百科,Facebook 甚至 Google 等技术巨头使用。 MariaDB 是一种可为 MySQL 提供插件替换功能的数据库服务器。开发人员的首要关注点是安全性,在每个版本发布时,开发人员还会合并所有 MySQL 的安全修补程序,并在需要时对其进行增强。
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短. 比如"文章按评论数降序排序"这个场景: 如果这样写,数据量大时肯定渣成狗. SELECT posts.id, posts.content, count(comments.id) AS comment_count FROM posts LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来 GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数 ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序 LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
引用来自“乌龟壳”的评论
倒着回
不开源不免费不跨平台这个是不是缺点不评价
如链接所证,SQL Server默认每条select都等于select for update。我猜是因为sqlserver面对的更多是傻瓜用户,默认读写互斥虽然性能差,但不容易写出有问题的并发逻辑,而且高级用户可以绕过这个限制。 https://docs.microsoft.com/en-us/sql/t-sql/statements/set-transaction-isolation-level-transact-sql 就算设置了让sqlserver用mvcc(READ_COMMITTED_SNAPSHOT=TRUE),也可以使用with(holdlock)这个hint来实现select for update https://docs.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table 所以你说的不支持select for update纯粹是全文搜索来的表面现象,sqlserver对锁的细粒度控制项比oracle的还多。
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短. 比如"文章按评论数降序排序"这个场景: 如果这样写,数据量大时肯定渣成狗. SELECT posts.id, posts.content, count(comments.id) AS comment_count FROM posts LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来 GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数 ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序 LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
引用来自“乌龟壳”的评论
倒着回
不开源不免费不跨平台这个是不是缺点不评价
如链接所证,SQL Server默认每条select都等于select for update。我猜是因为sqlserver面对的更多是傻瓜用户,默认读写互斥虽然性能差,但不容易写出有问题的并发逻辑,而且高级用户可以绕过这个限制。 https://docs.microsoft.com/en-us/sql/t-sql/statements/set-transaction-isolation-level-transact-sql 就算设置了让sqlserver用mvcc(READ_COMMITTED_SNAPSHOT=TRUE),也可以使用with(holdlock)这个hint来实现select for update https://docs.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table 所以你说的不支持select for update纯粹是全文搜索来的表面现象,sqlserver对锁的细粒度控制项比oracle的还多。
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短. 比如"文章按评论数降序排序"这个场景: 如果这样写,数据量大时肯定渣成狗. SELECT posts.id, posts.content, count(comments.id) AS comment_count FROM posts LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来 GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数 ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序 LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
倒着回
不开源不免费不跨平台这个是不是缺点不评价
如链接所证,SQL Server默认每条select都等于select for update。我猜是因为sqlserver面对的更多是傻瓜用户,默认读写互斥虽然性能差,但不容易写出有问题的并发逻辑,而且高级用户可以绕过这个限制。 https://docs.microsoft.com/en-us/sql/t-sql/statements/set-transaction-isolation-level-transact-sql 就算设置了让sqlserver用mvcc(READ_COMMITTED_SNAPSHOT=TRUE),也可以使用with(holdlock)这个hint来实现select for update https://docs.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table 所以你说的不支持select for update纯粹是全文搜索来的表面现象,sqlserver对锁的细粒度控制项比oracle的还多。
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短. 比如"文章按评论数降序排序"这个场景: 如果这样写,数据量大时肯定渣成狗. SELECT posts.id, posts.content, count(comments.id) AS comment_count FROM posts LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来 GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数 ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序 LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
还有,SQL Server什么时候支持SELECT FOR UPDATE这种读上锁的语句呢?不会现在还不支持吧,那可就要笑死人了哟.
引用来自“HYUO”的评论
ee神你已经“进化”到昧着良心睁眼说瞎话的程度了吗?默哀😂
引用来自“eechen”的评论
微软的SQL Server既不免费,也不开源,更不跨平台,甚至连很实用的读上锁SELECT FOR UPDATE都不支持,怎么跟MySQL比?
MySQL虽然不支持HASH JOIN,但其使用的是优化过的NESTED LOOP JOIN,而且一直在改进,比如5.6引入的MRR(Multi Range Read)和BKA(Batched Key Access),能大幅提升基于INDEX的NESTED LOOP JOIN的性能,Percona公司的拿MySQL 5.6用MRR和BKA化过的基于INDEX的NESTED LOOP JOIN跟MariaDB的HASH JOIN进行对比测试: http://www.tuicool.com/articles/nIFVNn 结论是: Also in the chart above the bottom two bars correspond to MariaDB with Hash Join and Key-ordered Scan enabled, and MariaDB with Hash Join and Key-ordered Scan disabled, and the only difference in query time is 48.78s vs 48.91s, so I don’t see Hash Join and Key-ordered Scan making much of a difference here.
I intend to run tests to see what specific types of queries would benefit from Hash Join as compared to Nested Loop Join, but for now it looks like Nested Loop Join is a much better general purpose join algorithm.
还有,SQL Server什么时候支持SELECT FOR UPDATE这种读上锁的语句呢?不会现在还不支持吧,那可就要笑死人了哟.
引用来自“HYUO”的评论
ee神你已经“进化”到昧着良心睁眼说瞎话的程度了吗?默哀😂
微软的SQL Server既不免费,也不开源,更不跨平台,甚至连很实用的读上锁SELECT FOR UPDATE都不支持,怎么跟MySQL比?
MySQL虽然不支持HASH JOIN,但其使用的是优化过的NESTED LOOP JOIN,而且一直在改进,比如5.6引入的MRR(Multi Range Read)和BKA(Batched Key Access),能大幅提升基于INDEX的NESTED LOOP JOIN的性能,Percona公司的拿MySQL 5.6用MRR和BKA化过的基于INDEX的NESTED LOOP JOIN跟MariaDB的HASH JOIN进行对比测试: http://www.tuicool.com/articles/nIFVNn 结论是: Also in the chart above the bottom two bars correspond to MariaDB with Hash Join and Key-ordered Scan enabled, and MariaDB with Hash Join and Key-ordered Scan disabled, and the only difference in query time is 48.78s vs 48.91s, so I don’t see Hash Join and Key-ordered Scan making much of a difference here.
I intend to run tests to see what specific types of queries would benefit from Hash Join as compared to Nested Loop Join, but for now it looks like Nested Loop Join is a much better general purpose join algorithm.
评论(37)
说这么多有什么用
请问.net高并发大数据+SqlServer还是+MySQL
MSSQL和MYSQL能放在一起比?真是可笑啊
怕是你没被MYSQL坑过,或者你是干JAVA的
否则,巨头将被虫子(JAVA,Python)蚕食
国内.net工资越来越低了,工作机会也越来越少了
别跟我讨论开源,最后哪个不是闭源赚钱,那么多中间件都不能用了,要么花钱,要么换替代品,真心累
引用来自“eechen”的评论
@乌龟壳 脱离实际应用场景谈JOIN算法优势都是耍流氓.就拿最常用的"查询某篇文章对应的评论"这个表连接场景来说:
SELECT * FROM posts, comments
WHERE posts.id = comments.pid AND posts.id = 1024;
肯定是NESTED LOOP JOIN算法有优势.
驱动表(外表): posts (因为有过滤条件 posts.id = 1024 所以记录数只有1条,绝对的小表)
查找表(内表): comments (comments.pid 上有索引,MySQL可以应用BKA批量顺序读索引优化)
就算Oracle这种支持多种JOIN算法的数据库,也肯定优先使用NESTED LOOP JOIN算法.
所以,因为MySQL不支持HASH JOIN,就说MySQL表连接速度一定不如那些支持HASH JOIN的数据库,纯属无稽之谈.
当然,那些尤其适合HASH JOIN发挥优势的表连接场景,MySQL肯定吃亏,但并非所有表连接场景都适合使用HASH JOIN.
小数据集驱动有索引的大表,这种场景就不适合HASH JOIN.
引用来自“乌龟壳”的评论
你一张口就有问题,我前面已经举例了,你拿着NL对抗HJ就像拿着select对抗update,有意义吗?再强调一下,你经常为了黑而黑,拿着用“全文搜索”拿来的,自己不理解的东西在比来比去,拿着表面的东西去说没有任何意义。
你是你的问题,至于H那位童鞋踩mysql踩得一文不值那是另一个问题。
不要觉得我在和你一样搞开源闭源斗争,我不是拉帮结派去围攻你,只是就事论事而已,也不是在支持H童鞋的观点。
引用来自“eechen”的评论
NESTED LOOP JOIN和HASH JOIN的对比肯定有意义呀.适合的场景使用适合的算法.
但那个软粉却非要说MySQL不支持HASH JOIN,所以表连接性能就一定差,这明显是错误的论调.
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短.
比如"文章按评论数降序排序"这个场景:
如果这样写,数据量大时肯定渣成狗.
SELECT
posts.id,
posts.content,
count(comments.id) AS comment_count
FROM posts
LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来
GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数
ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序
LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
但是如果直接在posts表中添加一个comment_count字段用于统计和排序即可,那速度就会快得飞起.
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
引用来自“乌龟壳”的评论
倒着回不开源不免费不跨平台这个是不是缺点不评价
如链接所证,SQL Server默认每条select都等于select for update。我猜是因为sqlserver面对的更多是傻瓜用户,默认读写互斥虽然性能差,但不容易写出有问题的并发逻辑,而且高级用户可以绕过这个限制。
https://docs.microsoft.com/en-us/sql/t-sql/statements/set-transaction-isolation-level-transact-sql
就算设置了让sqlserver用mvcc(READ_COMMITTED_SNAPSHOT=TRUE),也可以使用with(holdlock)这个hint来实现select for update
https://docs.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table
所以你说的不支持select for update纯粹是全文搜索来的表面现象,sqlserver对锁的细粒度控制项比oracle的还多。
引用来自“乌龟壳”的评论
关于你举的例子,正常的数据库都不会走hash join,hash join产生的前提是有较大的无索引的集合要连接。你的comments.post_id有索引,posts表也是全表都要,根本不会产生hash join的需要,NL加索引就是最快的了。假设在comments.post_id上没有索引,那么hash join就会产生了,说白了就是帮你建一条附属于语句的临时索引。
你可以说“我为啥那么傻不在comments.post_id上建立索引?”
其实问题就是你举得例子太简单还没涉及到hash join的真正场景。实际在OLAP里经常有几十上百行的SQL,它们做的是各种关联查询,重点是经常在一些通过group by、子查询等产生的临时子集合上再次进行的关联。这些东西用mysql去做就是各种临时表,查询不得不拆成一段一段,就因为mysql没法很好地优化这种复杂查询。
你说的扬长避短隐含的意思是我用我的长处代替我的短处不就行了吗?实际mysql在任何角度都没有在复杂查询上提供了“长处”,它就是做不到很好地处理。
我不想评价H的东西,因为你对他的话没理解到位(错觉),另外就是它说的也有一部分我不赞同的观点。但是不想在这跑题说。不过他说的hash join本身是没问题的。
引用来自“eechen”的评论
@乌龟壳 脱离实际应用场景谈JOIN算法优势都是耍流氓.就拿最常用的"查询某篇文章对应的评论"这个表连接场景来说:
SELECT * FROM posts, comments
WHERE posts.id = comments.pid AND posts.id = 1024;
肯定是NESTED LOOP JOIN算法有优势.
驱动表(外表): posts (因为有过滤条件 posts.id = 1024 所以记录数只有1条,绝对的小表)
查找表(内表): comments (comments.pid 上有索引,MySQL可以应用BKA批量顺序读索引优化)
就算Oracle这种支持多种JOIN算法的数据库,也肯定优先使用NESTED LOOP JOIN算法.
所以,因为MySQL不支持HASH JOIN,就说MySQL表连接速度一定不如那些支持HASH JOIN的数据库,纯属无稽之谈.
当然,那些尤其适合HASH JOIN发挥优势的表连接场景,MySQL肯定吃亏,但并非所有表连接场景都适合使用HASH JOIN.
小数据集驱动有索引的大表,这种场景就不适合HASH JOIN.
引用来自“乌龟壳”的评论
你一张口就有问题,我前面已经举例了,你拿着NL对抗HJ就像拿着select对抗update,有意义吗?再强调一下,你经常为了黑而黑,拿着用“全文搜索”拿来的,自己不理解的东西在比来比去,拿着表面的东西去说没有任何意义。
你是你的问题,至于H那位童鞋踩mysql踩得一文不值那是另一个问题。
不要觉得我在和你一样搞开源闭源斗争,我不是拉帮结派去围攻你,只是就事论事而已,也不是在支持H童鞋的观点。
引用来自“eechen”的评论
NESTED LOOP JOIN和HASH JOIN的对比肯定有意义呀.适合的场景使用适合的算法.
但那个软粉却非要说MySQL不支持HASH JOIN,所以表连接性能就一定差,这明显是错误的论调.
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短.
比如"文章按评论数降序排序"这个场景:
如果这样写,数据量大时肯定渣成狗.
SELECT
posts.id,
posts.content,
count(comments.id) AS comment_count
FROM posts
LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来
GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数
ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序
LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
但是如果直接在posts表中添加一个comment_count字段用于统计和排序即可,那速度就会快得飞起.
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
引用来自“乌龟壳”的评论
倒着回不开源不免费不跨平台这个是不是缺点不评价
如链接所证,SQL Server默认每条select都等于select for update。我猜是因为sqlserver面对的更多是傻瓜用户,默认读写互斥虽然性能差,但不容易写出有问题的并发逻辑,而且高级用户可以绕过这个限制。
https://docs.microsoft.com/en-us/sql/t-sql/statements/set-transaction-isolation-level-transact-sql
就算设置了让sqlserver用mvcc(READ_COMMITTED_SNAPSHOT=TRUE),也可以使用with(holdlock)这个hint来实现select for update
https://docs.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table
所以你说的不支持select for update纯粹是全文搜索来的表面现象,sqlserver对锁的细粒度控制项比oracle的还多。
假设在comments.post_id上没有索引,那么hash join就会产生了,说白了就是帮你建一条附属于语句的临时索引。
你可以说“我为啥那么傻不在comments.post_id上建立索引?”
引用来自“eechen”的评论
@乌龟壳 脱离实际应用场景谈JOIN算法优势都是耍流氓.就拿最常用的"查询某篇文章对应的评论"这个表连接场景来说:
SELECT * FROM posts, comments
WHERE posts.id = comments.pid AND posts.id = 1024;
肯定是NESTED LOOP JOIN算法有优势.
驱动表(外表): posts (因为有过滤条件 posts.id = 1024 所以记录数只有1条,绝对的小表)
查找表(内表): comments (comments.pid 上有索引,MySQL可以应用BKA批量顺序读索引优化)
就算Oracle这种支持多种JOIN算法的数据库,也肯定优先使用NESTED LOOP JOIN算法.
所以,因为MySQL不支持HASH JOIN,就说MySQL表连接速度一定不如那些支持HASH JOIN的数据库,纯属无稽之谈.
当然,那些尤其适合HASH JOIN发挥优势的表连接场景,MySQL肯定吃亏,但并非所有表连接场景都适合使用HASH JOIN.
小数据集驱动有索引的大表,这种场景就不适合HASH JOIN.
引用来自“乌龟壳”的评论
你一张口就有问题,我前面已经举例了,你拿着NL对抗HJ就像拿着select对抗update,有意义吗?再强调一下,你经常为了黑而黑,拿着用“全文搜索”拿来的,自己不理解的东西在比来比去,拿着表面的东西去说没有任何意义。
你是你的问题,至于H那位童鞋踩mysql踩得一文不值那是另一个问题。
不要觉得我在和你一样搞开源闭源斗争,我不是拉帮结派去围攻你,只是就事论事而已,也不是在支持H童鞋的观点。
引用来自“eechen”的评论
NESTED LOOP JOIN和HASH JOIN的对比肯定有意义呀.适合的场景使用适合的算法.
但那个软粉却非要说MySQL不支持HASH JOIN,所以表连接性能就一定差,这明显是错误的论调.
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短.
比如"文章按评论数降序排序"这个场景:
如果这样写,数据量大时肯定渣成狗.
SELECT
posts.id,
posts.content,
count(comments.id) AS comment_count
FROM posts
LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来
GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数
ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序
LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
但是如果直接在posts表中添加一个comment_count字段用于统计和排序即可,那速度就会快得飞起.
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
不开源不免费不跨平台这个是不是缺点不评价
如链接所证,SQL Server默认每条select都等于select for update。我猜是因为sqlserver面对的更多是傻瓜用户,默认读写互斥虽然性能差,但不容易写出有问题的并发逻辑,而且高级用户可以绕过这个限制。
https://docs.microsoft.com/en-us/sql/t-sql/statements/set-transaction-isolation-level-transact-sql
就算设置了让sqlserver用mvcc(READ_COMMITTED_SNAPSHOT=TRUE),也可以使用with(holdlock)这个hint来实现select for update
https://docs.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table
所以你说的不支持select for update纯粹是全文搜索来的表面现象,sqlserver对锁的细粒度控制项比oracle的还多。
引用来自“eechen”的评论
@乌龟壳 脱离实际应用场景谈JOIN算法优势都是耍流氓.就拿最常用的"查询某篇文章对应的评论"这个表连接场景来说:
SELECT * FROM posts, comments
WHERE posts.id = comments.pid AND posts.id = 1024;
肯定是NESTED LOOP JOIN算法有优势.
驱动表(外表): posts (因为有过滤条件 posts.id = 1024 所以记录数只有1条,绝对的小表)
查找表(内表): comments (comments.pid 上有索引,MySQL可以应用BKA批量顺序读索引优化)
就算Oracle这种支持多种JOIN算法的数据库,也肯定优先使用NESTED LOOP JOIN算法.
所以,因为MySQL不支持HASH JOIN,就说MySQL表连接速度一定不如那些支持HASH JOIN的数据库,纯属无稽之谈.
当然,那些尤其适合HASH JOIN发挥优势的表连接场景,MySQL肯定吃亏,但并非所有表连接场景都适合使用HASH JOIN.
小数据集驱动有索引的大表,这种场景就不适合HASH JOIN.
引用来自“乌龟壳”的评论
你一张口就有问题,我前面已经举例了,你拿着NL对抗HJ就像拿着select对抗update,有意义吗?再强调一下,你经常为了黑而黑,拿着用“全文搜索”拿来的,自己不理解的东西在比来比去,拿着表面的东西去说没有任何意义。
你是你的问题,至于H那位童鞋踩mysql踩得一文不值那是另一个问题。
不要觉得我在和你一样搞开源闭源斗争,我不是拉帮结派去围攻你,只是就事论事而已,也不是在支持H童鞋的观点。
适合的场景使用适合的算法.
但那个软粉却非要说MySQL不支持HASH JOIN,所以表连接性能就一定差,这明显是错误的论调.
使用MySQL就是要尽量避免写出依赖HASH JOIN来提升性能的表连接语句,扬长避短.
比如"文章按评论数降序排序"这个场景:
如果这样写,数据量大时肯定渣成狗.
SELECT
posts.id,
posts.content,
count(comments.id) AS comment_count
FROM posts
LEFT JOIN comments ON posts.id = comments.post_id --左连接,保证左表posts中没有评论的文章也显示出来
GROUP BY posts.id --分组,配合count(comments.id)统计到每篇文章的评论数
ORDER BY comment_count DESC, posts.id DESC --按评论数排序,相同则按文章ID排序
LIMIT 2 OFFSET (3-1)*2 --分页,2表示每页显示的文章数量,3表示第3页
但是如果直接在posts表中添加一个comment_count字段用于统计和排序即可,那速度就会快得飞起.
还有,我说SQL Server不免费开源跨平台以及不支持SELECT FOR UPDATE的写法,难道不是事实么?
引用来自“eechen”的评论
@乌龟壳 脱离实际应用场景谈JOIN算法优势都是耍流氓.就拿最常用的"查询某篇文章对应的评论"这个表连接场景来说:
SELECT * FROM posts, comments
WHERE posts.id = comments.pid AND posts.id = 1024;
肯定是NESTED LOOP JOIN算法有优势.
驱动表(外表): posts (因为有过滤条件 posts.id = 1024 所以记录数只有1条,绝对的小表)
查找表(内表): comments (comments.pid 上有索引,MySQL可以应用BKA批量顺序读索引优化)
就算Oracle这种支持多种JOIN算法的数据库,也肯定优先使用NESTED LOOP JOIN算法.
所以,因为MySQL不支持HASH JOIN,就说MySQL表连接速度一定不如那些支持HASH JOIN的数据库,纯属无稽之谈.
当然,那些尤其适合HASH JOIN发挥优势的表连接场景,MySQL肯定吃亏,但并非所有表连接场景都适合使用HASH JOIN.
小数据集驱动有索引的大表,这种场景就不适合HASH JOIN.
再强调一下,你经常为了黑而黑,拿着用“全文搜索”拿来的,自己不理解的东西在比来比去,拿着表面的东西去说没有任何意义。
你是你的问题,至于H那位童鞋踩mysql踩得一文不值那是另一个问题。
不要觉得我在和你一样搞开源闭源斗争,我不是拉帮结派去围攻你,只是就事论事而已,也不是在支持H童鞋的观点。
就拿最常用的"查询某篇文章对应的评论"这个表连接场景来说:
SELECT * FROM posts, comments
WHERE posts.id = comments.pid AND posts.id = 1024;
肯定是NESTED LOOP JOIN算法有优势.
驱动表(外表): posts (因为有过滤条件 posts.id = 1024 所以记录数只有1条,绝对的小表)
查找表(内表): comments (comments.pid 上有索引,MySQL可以应用BKA批量顺序读索引优化)
就算Oracle这种支持多种JOIN算法的数据库,也肯定优先使用NESTED LOOP JOIN算法.
所以,因为MySQL不支持HASH JOIN,就说MySQL表连接速度一定不如那些支持HASH JOIN的数据库,纯属无稽之谈.
当然,那些尤其适合HASH JOIN发挥优势的表连接场景,MySQL肯定吃亏,但并非所有表连接场景都适合使用HASH JOIN.
小数据集驱动有索引的大表,这种场景就不适合HASH JOIN.
引用来自“eechen”的评论
Oracle收购MySQL后,依旧使用GPL开源MySQL,否则哪来的Percona Server和MariaDB分支?Oracle收购MySQL后,陆续推出了5.5,5.6,5.7甚至8都已经在路上,又怎么能说由于更新缓慢而落后于其他数据库?
http://db-engines.com/en/ranking
要知道,MySQL排名甚至已经威胁到第一的Oracle,并且在Oracle接手后迅速超过了SQL Server.
而且在Oracle收购SUN得到MySQL前就已经收购了现在MySQL默认的事务引擎InnoDB.
看不起Oracle的,要不你拿出个10亿美元+的前去收购芬兰的InnoDB和MySQL呀.
阿里的AliSQL就是基于Oracle的MySQL 5.6进行开发:
https://github.com/alibaba/AliSQL
Changes in AliSQL 5.6.32 (2017-05-04)
引用来自“HYUO”的评论
Hash Join支持没?并行查询支持没?光频繁更新版本有嘛用,看看PostgreSQL每发布一个新版本支持多少功能吧。引用来自“eechen”的评论
来来来,请软粉大神谈谈 hash join 在开发中的不可或缺和作用, 谈谈阿里因为用了不支持 hash join 的MySQL导致那些功能无法实现, 无法最大化用户体验和服务器性能, 哈哈. 有些功能在大并发下就如同外键一样鸡肋. 软粉赶紧为 SQL Server 鼓吹造势再行, 否则没人用了.引用来自“HYUO”的评论
阿里那所谓的大并发不就是狂堆机器吗?当然阿里架构的扩展性还是很强的,MySQL单机性能不行,阿里只能进行大量的水平扩展,要是换成PG无疑可以大幅减少DB的部署数量,MySQL只要一涉及多表链接的大数据复杂查询性能就大降,这就是不支持Hash Join的代价,还有SQL Server就不用ee神操心了,DB-Engines年度数据库和每年两位数增长的营收说明一切。😆引用来自“eechen”的评论
人家MySQL的性能就不劳软粉费心了,行级锁,事务写,多线程轻松利用多核,以及利用复制实现集群,实在是成熟.最喜欢堆机器的的数据库铁定是SQL Server,因为Windows服务器性能不行,SQL Server也不行,所以SQL Server只能搞跨平台来借助Linux来提升性能了.话说SQL Server什么时候像MySQL那样免费开源跨平台呀?哈哈.还有,SQL Server什么时候支持SELECT FOR UPDATE这种读上锁的语句呢?不会现在还不支持吧,那可就要笑死人了哟.
引用来自“HYUO”的评论
ee神你已经“进化”到昧着良心睁眼说瞎话的程度了吗?默哀😂引用来自“eechen”的评论
微软的SQL Server既不免费,也不开源,更不跨平台,甚至连很实用的读上锁SELECT FOR UPDATE都不支持,怎么跟MySQL比?MySQL虽然不支持HASH JOIN,但其使用的是优化过的NESTED LOOP JOIN,而且一直在改进,比如5.6引入的MRR(Multi Range Read)和BKA(Batched Key Access),能大幅提升基于INDEX的NESTED LOOP JOIN的性能,Percona公司的拿MySQL 5.6用MRR和BKA化过的基于INDEX的NESTED LOOP JOIN跟MariaDB的HASH JOIN进行对比测试:
http://www.tuicool.com/articles/nIFVNn
结论是:
Also in the chart above the bottom two bars correspond to
MariaDB with Hash Join and Key-ordered Scan enabled,
and MariaDB with Hash Join and Key-ordered Scan disabled,
and the only difference in query time is 48.78s vs 48.91s,
so I don’t see Hash Join and Key-ordered Scan making much of a difference here.
I intend to run tests to see what specific types of queries would benefit from Hash Join
as compared to Nested Loop Join,
but for now it looks like Nested Loop Join
is a much better general purpose join algorithm.
所以,到底是谁昧着良心说MySQL只是发版本而没有优化JOIN算法呢?
还有谁说HASH JOIN性能就一定比优化过的NESTED LOOP JOIN快?
拿hash join比netsted loop也能拿上来比,就像拿select和update比一样——他们都是语句啊,select用的锁比较少,所以update垃圾啊。
至于你和别人争论的其它东西我不评论。
引用来自“eechen”的评论
Oracle收购MySQL后,依旧使用GPL开源MySQL,否则哪来的Percona Server和MariaDB分支?Oracle收购MySQL后,陆续推出了5.5,5.6,5.7甚至8都已经在路上,又怎么能说由于更新缓慢而落后于其他数据库?
http://db-engines.com/en/ranking
要知道,MySQL排名甚至已经威胁到第一的Oracle,并且在Oracle接手后迅速超过了SQL Server.
而且在Oracle收购SUN得到MySQL前就已经收购了现在MySQL默认的事务引擎InnoDB.
看不起Oracle的,要不你拿出个10亿美元+的前去收购芬兰的InnoDB和MySQL呀.
阿里的AliSQL就是基于Oracle的MySQL 5.6进行开发:
https://github.com/alibaba/AliSQL
Changes in AliSQL 5.6.32 (2017-05-04)
引用来自“HYUO”的评论
Hash Join支持没?并行查询支持没?光频繁更新版本有嘛用,看看PostgreSQL每发布一个新版本支持多少功能吧。引用来自“eechen”的评论
来来来,请软粉大神谈谈 hash join 在开发中的不可或缺和作用, 谈谈阿里因为用了不支持 hash join 的MySQL导致那些功能无法实现, 无法最大化用户体验和服务器性能, 哈哈. 有些功能在大并发下就如同外键一样鸡肋. 软粉赶紧为 SQL Server 鼓吹造势再行, 否则没人用了.引用来自“HYUO”的评论
阿里那所谓的大并发不就是狂堆机器吗?当然阿里架构的扩展性还是很强的,MySQL单机性能不行,阿里只能进行大量的水平扩展,要是换成PG无疑可以大幅减少DB的部署数量,MySQL只要一涉及多表链接的大数据复杂查询性能就大降,这就是不支持Hash Join的代价,还有SQL Server就不用ee神操心了,DB-Engines年度数据库和每年两位数增长的营收说明一切。😆引用来自“eechen”的评论
人家MySQL的性能就不劳软粉费心了,行级锁,事务写,多线程轻松利用多核,以及利用复制实现集群,实在是成熟.最喜欢堆机器的的数据库铁定是SQL Server,因为Windows服务器性能不行,SQL Server也不行,所以SQL Server只能搞跨平台来借助Linux来提升性能了.话说SQL Server什么时候像MySQL那样免费开源跨平台呀?哈哈.还有,SQL Server什么时候支持SELECT FOR UPDATE这种读上锁的语句呢?不会现在还不支持吧,那可就要笑死人了哟.
引用来自“HYUO”的评论
ee神你已经“进化”到昧着良心睁眼说瞎话的程度了吗?默哀😂MySQL虽然不支持HASH JOIN,但其使用的是优化过的NESTED LOOP JOIN,而且一直在改进,比如5.6引入的MRR(Multi Range Read)和BKA(Batched Key Access),能大幅提升基于INDEX的NESTED LOOP JOIN的性能,Percona公司的拿MySQL 5.6用MRR和BKA化过的基于INDEX的NESTED LOOP JOIN跟MariaDB的HASH JOIN进行对比测试:
http://www.tuicool.com/articles/nIFVNn
结论是:
Also in the chart above the bottom two bars correspond to
MariaDB with Hash Join and Key-ordered Scan enabled,
and MariaDB with Hash Join and Key-ordered Scan disabled,
and the only difference in query time is 48.78s vs 48.91s,
so I don’t see Hash Join and Key-ordered Scan making much of a difference here.
I intend to run tests to see what specific types of queries would benefit from Hash Join
as compared to Nested Loop Join,
but for now it looks like Nested Loop Join
is a much better general purpose join algorithm.
所以,到底是谁昧着良心说MySQL只是发版本而没有优化JOIN算法呢?
还有谁说HASH JOIN性能就一定比优化过的NESTED LOOP JOIN快?
引用来自“梅开源”的评论
sqlite 做简单web应用很好的。轻便,开发者一个人管着,尽在掌握。凡事有利有弊,经过几次oracle被DBA弄出问题和各种权限问题锁问题存储空间问题后,我现在觉得简单应用自己一个人sqlite搞定最稳。引用来自“Jay_M_Hu”的评论
并发写不太好,并发读倒是很强。引用来自“eechen”的评论
可以考虑这样配置来提升写性能,在打开SQLite数据库后执行以下语句:PRAGMA journal_mode = WAL; --写时读(要求SQLite >= 3.7.0)
PRAGMA synchronous = OFF; --异步写(默认是FULL同步写)
http://sqlite.org/pragma.html#pragma_synchronous
关闭同步时,写操作不用等到数据真正写到磁盘后就能返回,可实现异步写.
运行SQLite的程序(比如PHP-FPM进程)崩溃,数据库文件不会损坏,
但在系统崩溃或写入数据时意外断电的情况下则可能会损坏.
批量插入时开启事务也能大幅提升插入性能.
还有可以考虑将SQLite文件置于Linux内存文件系统/dev/shm上提升写入性能.