发送数据非常慢或RDS

我有一个基本的SELECT语句的以下两个configuration文件:

 select count(*) from mturk_completion; 

这里是两个configuration文件:

 # My Local machine, using a local db Status Duration starting 0.000045 checking permissions 0.000006 Opening tables 0.000015 init 0.000011 System lock 0.000006 optimizing 0.000004 statistics 0.000011 preparing 0.000009 executing 0.000002 Sending data 0.034015 ######## end 0.000012 query end 0.000006 closing tables 0.000011 freeing items 0.000036 cleaning up 0.000010 

然后在这里使用RDS mysql db在我的AWS ec2大型实例上:

 starting 0.000068 checking permissions 0.000016 Opening tables 0.000028 init 0.000024 System lock 0.000018 optimizing 0.000015 statistics 0.000022 preparing 0.000022 executing 0.000012 Sending data 0.446171 ######### end 0.000036 query end 0.000018 closing tables 0.000023 freeing items 0.00009 cleaning up 0.000013 

除了发送数据部分在RDS实例上慢了十倍之外,大多数数字是可比较的! 有什么可以解释,我将如何解决这个问题?

这是RDS实例信息:

在这里输入图像说明

发送数据

线程正在读取和处理SELECT语句的行,并将数据发送到客户端。 因为在这个状态期间发生的操作倾向于执行大量的磁盘访问(读取) ,所以在给定查询的整个生命周期中,它通常是运行时间最长的状态。

http://dev.mysql.com/doc/refman/5.0/en/general-thread-states.html

我怀疑磁盘访问速度是不同的。

在你的第一个testing中,似乎你有一台本地机器连接到本地数据库服务器和本地硬盘。 在你的第二个testing中,你使用远程硬盘(即EBS)连接到远程数据库服务器。

EBS(这是RDS用于存储的)比实例存储要慢很多,我想可能还是会比工作站上卸载的本地磁盘慢(特别是在有SSD的情况下)。

然而,为了换取性能上的损失,您可以从ELB的抽象性中获得许多好处:

  • 能够拍摄实例的快照并从快照中启动新的实例
  • 调整磁盘大小的能力
  • 改变磁盘性能的能力(通过预置IOPS)
  • 将RDS实例透明地移动到可能在重新启动或实例types更改期间发生的新主机的能力

这就是为什么大多数人会接受性能处罚。

如果性能损失是显着的,那么你可以尝试几件事情:

  • 预置IOPS
  • 使用实例存储在EC2上运行您自己的MySQL实例。 我不推荐这样做,因为如果您的实例被停止,要避免数据丢失将非常困难,而且如果数据增长,您将无法调整磁盘的大小。
  • 在EC2上使用EBS在RAID上运行您自己的MySQL实例
  • 水平扩展,如果主服务器上的IO成为瓶颈,则添加只读副本
  • 在您的应用程序中实现数据caching