2009-11-23 167 views
12

我一直在努力解决只有当数据库空闲了一段时间才能查询数据的问题。第一个查询将非常缓慢,大约30秒,然后相关的查询将快速如0.1秒。我认为这与缓存有关,但我一直无法找到它的原因。mysql第一次查询速度慢,然后快速查询相关查询

将mysql变量tmp_table_size,max_heap_table_size更改为更大的大小除了在内存中创建临时表之外没有任何效果。

我不认为这与查询本身有关,因为索引很好,并且在第一个慢查询之后,同一查询的变体不会显示在慢查询日志中。我最有兴趣试图确定此问题的原因或重置有问题的缓存的方法,以便我可以解决问题。

+3

我不是MySQL的专家,但你也许应该补充的MySQL版本中, OS信息和引擎信息(MyISAM,InnoDB?) – 2009-11-23 23:51:56

+0

好的建议,5.0.26-standard-log和InnoDB。
Linux 2.4.21-47.ELsmp#1 SMP Wed Jul 5 20:30:30 EDT 2006 x86_64 x86_64 x86_64 GNU/Linu – 2009-11-24 00:07:39

+0

这属于http://www.serverfault.com – 2009-11-24 21:47:34

回答

7

innodb数据文件的页面缓存在innodb缓冲池中。这是你所期望的。即使在好的硬盘驱动器上读取文件也很慢,尤其是随机读取,这主要是数据库看到的。

这可能是您的第一个查询正在进行某种表扫描,将大量页面拉入缓冲池,然后访问它们的速度很快。或类似的东西。

这是我所期望的。

理想情况下,对所有表使用相同的引擎(例外:系统表,临时表(可能)和非常小的表或短期的表)。如果你不这样做,那么他们必须争取公羊。

假设您的所有表都是innodb,请使缓冲池使用高达服务器物理内存的75%(假设您不在计算机上运行太多其他任务)。

然后,你将能够将12G左右的数据库转换为内存,所以一旦“热身”,数据库的“最常用”12G将会出现在内存中,访问数据库的速度非常快。

的MySQL的一些用户倾向于“热身”生产服务器之后通过发送他们从其他机器复制查询了一段时间重新启动(这将是复制的奴隶),直到他们增加他们进入他们的生产池。这可以避免缓存很冷时出现的极端缓慢。例如,YouTube做到这一点(或至少它曾经,谷歌收购了他们,他们现在可以使用谷歌-FU)

+0

答案竟然是改变mysql配置文件并调整innodb。随着innodb变量的大小增加,数据库现在会在几次查询后进行热身。我猜想发生了什么是缓存太小,无法在内存中使用所有表索引,因此它不断从磁盘交换,从而导致首次查询缓慢。现在它已经足以让他们都记忆犹新,所以问题没有了。 – 2009-12-03 18:22:46

+0

我的问题是,是否有可能使第一个查询更快?或者它是什么,并且增加缓冲池是正确的方法? – 2017-06-18 17:44:21

3

你的mysql服务器上还有其他东西在运行吗?我的想法是,也许在第一次查询后,你的表仍然被缓存在内存中。一旦闲置,另一个进程将导致它被解除缓存。只是一个猜测。

你有多少内存还有其他什么东西在运行?

+0

mysql是唯一运行的服务器。它有16Gb的内存。我同意将它从内存中取消缓存,但我无法弄清楚它在哪里缓存,因此我可以解决问题。我不知道它是否是一个MySQL配置问题,Linux配置问题,SQL问题等。我已经搜索了其他人有同样的问题,但没有任何问题的洞察力。 – 2009-11-24 00:05:16

+0

基于此:http://dev.mysql.com/doc/refman/5.1/en/query-cache.html,也许尝试使query_cache_size更大。这很奇怪,因为无论MySQL是否告诉它,Linux都应该自动保存这些东西。你也可以尝试通用的方法来加快你的查询速度,比如添加一个索引并且没有大表,但是我不知道这些会对你有帮助。 – 2009-11-24 00:11:09

+0

query_cache_size设置为零,所以这不是问题。我想知道什么是缓存它。 – 2009-11-24 00:14:22

0

在一段时间之后运行查询时,以及在重新运行查询并快速获得结果时,在Linux命令行上输入并比较“vmstat 1”的输出。具体检查“bi”列(即每秒从磁盘读取的kb)。

您可能会发现操作系统在快速情况下缓存磁盘块(因此为较低的“双”数字),但缓慢情况下(因此为较大的“双”数字)不会缓存磁盘块。

您可能还会发现,无论是哪种情况,vmstat都会显示CPU的高/低使用率。如果速度较慢,并且磁盘吞吐量也很低,则即使您已指示相关配置值设置为零,系统仍可能会返回缓存查询。也许检查show engine innodb statusSHOW VARIABLES的输出并确认。

innodb_buffer_pool_size也可能被设置为高(应该是......),甚至在操作系统可以返回之前它们会缓存这些块。

您可能还会发现“key_buffer”设置得很高 - 这会将索引缓存到索引中,这可能会使您的选择非常快速。

请尝试检查mysql performance blog网站的大量有用的信息。

+0

这是怎么回事。服务器正在从第一个查询的磁盘读取innodb表,然后在运行类似查询时使用缓存。现在我必须弄清楚如何减小ibdata1的大小。考虑到转移到innodb_file_per_table – 2009-12-02 18:33:06

1

我有一个SSIS包被超时。查询非常简单,只需一个MySQL表,但它有时会返回很多记录,有时最初需要几分钟才能执行,然后如果我想再次查询,那么只需几毫秒。我们被ADO连接困住了,这意味着它会在30秒后超时,所以我们试图加载的数据库大约有一半失败。

打我的头靠在我第一次尝试进行初始查询墙后;非常简单,只返回几行。由于它非常简单,因此可以快速执行,并将表设置在缓存中以加快查询速度。在包的下一步中,我会做更复杂的查询,它返回保持超时的大数据集。解决的问题 - 加载所有表格。我可以定期开始这样做,通过首先执行一个简单的查询,复杂的查询执行得更快。

+0

所以你说你可以在比单独的大查询更少的时间内执行一个小查询加上你的原始大查询?你会认为MySQL会想出来,并在尝试大型查询之前将所需内容移到内存中。 – mpen 2013-01-28 22:53:36

0

我有问题,当MySQL 5.6在第一次查询后空闲时间过慢。这是一个连接问题,而不是MySQL实例问题,例如如果你运行MYSQL查询浏览器,执行“select * from some_queue”,将它放置几个小时,然后执行任何查询,它运行缓慢,同时浏览器的服务器或新实例上的进程将从相同的表中选择即刻。

添加跳跃主机缓存,跳过名称解析为my.ini文件解决了这个问题。

我不知道那是为什么。为什么我尝试这样做:没有这些选项的MySQL 5.1正在慢慢建立来自其他网络的连接(例如,服务器是192.168.1.100,192.168.1.101连接速度快,192.168.2.100连接速度慢),MySQL 5.6没有这样的问题开始如此我们最初并没有将这些添加到my.ini中。

UPD:解决了一半的情况下,实际上。将wait_timeout设置为最大整数固定了另一半。也许我现在可以删除跳跃主机缓存,跳过名称解析,它不会在的情况下,100%放慢