Chinaunix首页 | 论坛 | 博客
  • 博客访问: 52843
  • 博文数量: 6
  • 博客积分: 121
  • 博客等级: 入伍新兵
  • 技术积分: 104
  • 用 户 组: 普通用户
  • 注册时间: 2011-12-23 13:24
文章分类
文章存档

2012年(6)

分类: Mysql/postgreSQL

2012-01-09 20:49:14

之前用 MySQL 的 C API 的时候,里面提到了获取查询结果的时候,有 2 个函数: 和 。其中的主要差别为 mysql_store_result() 是一次性的把所有的结果都读取到 Client 的内存里面的,而 mysql_use_result() 则只是读取一部分,需要 Client 不断的调用  来获取剩下的数据。

当时我就有个疑问:当 Client 发送 SQL 语句给 MySQL 服务端以后,服务端是怎么返回数据的,如果为 mysql_store_result(),那么应该是一次性的将所有结果都返回的。那么 mysql_use_result() 呢?是每次调用 mysql_fetch_row() 的时候,从服务端读取一点数据回来,还是其他方法?

如果采用 mysql_use_result(),mysql_fetch_row() 是每次从服务器读取一点数据的话,那么这个对性能应该是有比较明显的影响的,这样在开发的时候,对于到底是否采用 mysql_use_result() 还是 mysql_store_result() 有需要有更多的关心。

为了分析这个问题,我写了一个简单的小程序,然后采用 wireshark 来抓包。

验证下来:
1. 从协议上来看,mysql_real_query() 执行的时候,Client 端就将 SQL 发送给服务端了,服务端不会等待其他协议,很快就直接返回查询的结果。
2. 服务端返回的结果中,不会包含有多少条结果,所以最后有多少条结果,是由 Client 端自己算出来的。
3. 服务端一开始就会返回有多少个字段,每个字段的名称和属性。所以执行例如 mysql_fetch_field() 这样的函数是不会再向服务端发送请求的。
4. 服务端然后再返回每条记录的数据。这个时候 Client 有可能还没有执行 mysql_use_result() 或者 mysql_store_result() 的!也就是说,mysql_use_result() 和 mysql_store_result() 在协议层次上,是一样的协议。
5. 服务端数据发送完毕的时候,有特别的一个数据发送过来表明数据发送完毕了。
6. 那么 mysql_store_result() 的实现,应该是一直读取数据,直到读取完毕了为止。而 mysql_use_result(),则应该是一部分一部分的读取的,如果返回的数据超过了 TCP 的缓冲区大小,那么 MySQL 服务端的处理线程应该会堵塞在例如 write() 这样的函数上。

7. 放心的使用 mysql_use_result() 吧,性能还是很好的。


这几天学 Java,MySQL for JDBC 的驱动的代码中,好像没有明确区分出来 use or store 这样的方式,以后有空了再仔细看看。

阅读(3702) | 评论(2) | 转发(2) |
给主人留下些什么吧!~~

皮娃娃哈哈2012-01-21 00:38:51

学习了!

7大爷2012-01-12 22:16:39

放心的使用 mysql_use_result() 吧,性能还是很好的