从性能角度来看,将MySQL临时表用于高度使用的网站功能的效率如何?

Rea*_*ues 10 php mysql performance temp-tables database-performance

我正在尝试为网站编写搜索功能,我已经决定使用MySQL临时表来处理数据输入的方法,通过以下查询:

CREATE TEMPORARY TABLE `patternmatch`
  (`pattern` VARCHAR(".strlen($queryLengthHere)."))

INSERT INTO `patternmatch` VALUES ".$someValues
Run Code Online (Sandbox Code Playgroud)

$someValues具有布局的一组数据在哪里('some', 'search', 'query')- 或者基本上是用户搜索的数据.然后我images根据表中的数据搜索我的主表,patternmatch如下所示:

SELECT images.* FROM images JOIN patternmatch ON (images.name LIKE patternmatch.pattern)
Run Code Online (Sandbox Code Playgroud)

然后我根据每个结果与输入匹配的程度应用启发式或评分系统,并通过启发式等显示结果.

我想知道创建临时表需要多少开销?我知道它们只存在于会话中,并在会话结束后立即被删除,但如果我每秒有数十万次搜索,我会遇到什么样的性能问题?有没有更好的方法来实现搜索功能?

nic*_*nda 6

您所说的完全正确,临时表只对当前用户/连接可见.仍然存在一些开销和一些其他问题,例如:

  • 对于您要创建和填充该表的数千个搜索中的每一个(并在以后删除) - 不是每个用户,每次搜索.因为每次搜索都很可能会重新执行脚本,而"每个会话"并不意味着PHP会话 - 它意味着数据库会话(开放连接).
  • 您将需要CREATE TEMPORARY TABLES可能没有的特权.
  • 不过,那个表真的应该有MEMORY类型,它会比你看起来更多地窃取你的RAM.因为即使有VARCHAR,MEMORY表也使用固定长度的行存储.
  • 如果您的启发式方法稍后需要两次引用该表(例如SELECT xyz FROM patternmatch AS pm1, patternmatch AS pm2 ...) - 这对于MEMORY表是不可能的.

接下来,您和数据库将更容易LIKE '%xyz%'直接添加到imagestables WHERE子句中.如果没有创建TEMP TABLE并加入它的开销,它也会这样做.

在任何情况下 - 无论你走哪条路 - 那将是非常缓慢的.即使您在其上添加索引images.name也很可能需要LIKE '%xyz%'代替 LIKE 'xyz%',因此索引将不会被使用.

我问的是一个特定于会话的临时表来处理用户的搜索输入(在搜索上创建,在会话结束时删除)是否是处理搜索功能的适当方式.

不.:)

替代选择

MySQL有一个内置的全文搜索(自从5.6也适用于InnoDB)甚至可以给你那个得分:我强烈建议给它一个读取和尝试.您可以确定数据库比您更了解如何有效地进行搜索.

如果您打算使用MyISAM而不是InnoDB,请注意FULLTEXT搜索时经常被忽略的限制,如果结果数少于总表行的50%,则只返回任何内容.

您可能想要查看的其他内容,例如Solr(Nice介绍阅读该主题本身将是http://en.wikipedia.org/wiki/Apache_Solr的开头).我们在公司使用它并且它做得很好,但它需要相当多的学习.

摘要

当前问题本身(搜索)的解决方案是使用FULLTEXT功能.

如果我每秒有数十万次搜索,我会遇到什么样的性能问题?有没有更好的方法来实现搜索功能?

为了给你一个数字,每秒10.000次呼叫并非"微不足道" - 每秒有数十万次搜索,你会遇到的性能问题在你的设置中无处不在.你将需要一些服务器,负载平衡和大量其他惊人的技术废话.其中一个将是例如Solr;)