使用PHP类来运行像这样糟糕的mysql查询吗?

时间:2010-01-09 02:21:29

标签: php mysql

我一直在看一些数据库(MySQL)包装器类,很多都是这样工作的,
1)运行sql查询
2)在获取关联的mysql数组时,他们通过结果并将它们添加到自己的数组中 3)然后你将运行如下所示的类并循环遍历它的数组

<?php  
$database = new Database();

$result = $database->query('SELECT * FROM user;');

foreach ($result as $user){
    echo $user->username;
}

?>

所以我的问题是,在高流量类型网站上这不是很好吗?我问,因为据我所知,mysql返回一个吃内存的数组,然后你从该数组构建一个新数组,然后循环遍历新数组。这不好还是不太正常?

3 个答案:

答案 0 :(得分:3)

简短的回答是:它很糟糕,非常糟糕。

麻烦的是你通过迭代两次结果来支付令人讨厌的性能损失(周期和内存!)。 (如果你有1000行返回怎么办?你得到所有数据,循环1000次,将它全部保存在内存中,然后再循环遍历它。)

如果稍微重构一下你的类,你仍然可以包装查询和fetch,但是你需要在查询之外执行fetch_array。在这种情况下,您可以在完成后立即从内存中丢弃每一行,这样您就不需要存储整个结果集,只需循环一次。

IIRC,PHP不会将整个MySQL结果集加载到内存中,基本上,当你调用mysql_fetch_array时,你要求集合中的下一行,只有在询问它时才加载,所以你“仅仅通过运行原始查询就不会为完整集(在PHP端)支付内存命中率。当你使用mysql_query(感谢VolkerK)时,整个结果被加载到内存中,但是你还在支付CPU花费两倍,这可能是一个重大的惩罚。

答案 1 :(得分:0)

代码很好。

foreach()只是在每次传递时移动数组指针。

你可以在这里阅读所有相关内容:

http://php.net/foreach

为了更深入地理解,请查看指针在C中的工作方式:

http://home.netcom.com/~tjensen/ptr/ch2x.htm

没有复制,迭代几乎总是通过递增指针来执行。

答案 2 :(得分:0)

这种查询非常正常。如果可以的话,最好一次只获取一行,但对于小型和分页查询所获得的那种普通小型数据集,额外的内存利用率并不重要。

但是,如果每个用户行中有大量用户和大量信息,那么

SELECT * FROM user肯定会生成一个无用的大数据集。尽量将选中的列数和行数保持在最小值,这是您实际要放在页面上的信息。