我遇到了我之前问过的问题/问题 –如何优化 AVG 查询的表?事实证明,@MichaelT 在一件事上是对的——使用 PHP 计算 AVG 比使用 MySQL 更快(比如使用 500 万条记录和 24 GB RAM 机器计算 AVG 速度快 80%)。
它并不总是一种选择。但是,请考虑此代码示例(数据集大小为 5m 条记录)。
MySQL的方式。
1)聚合数据(创建临时数据)(500ms)
CREATE TEMPORARY TABLE `temporary_grouped_data` AS
(
SELECT
`r1`.`id`,
`c1`.`wt`,
`c1`.`cpu`,
`c1`.`mu`,
`c1`.`pmu`
FROM
`requests` `r1`
INNER JOIN
`request_hosts` `rh1`
ON
`rh1`.`id` = `r1`.`request_host_id`
INNER JOIN
`request_uris` `ru1`
ON
`ru1`.`id` = `r1`.`request_uri_id`
INNER JOIN
`calls` `c1`
ON
`c1`.`id` = `r1`.`request_caller_id`
WHERE
1=1 {$sql_query['where']}
);
2) 获得整体 AVG (300ms)
SELECT COUNT(`id`), MIN(`wt`), MAX(`wt`), AVG(`wt`), MIN(`cpu`), MAX(`cpu`), AVG(`cpu`), MIN(`mu`), MAX(`mu`), AVG(`mu`), MIN(`pmu`), MAX(`pmu`), AVG(`pmu`) FROM `temporary_grouped_data`;
3) 计算第 95 个百分位数 (200ms)
SELECT `wt` FROM `temporary_grouped_data` ORDER BY `wt` ASC LIMIT 1726, 1;
SELECT `cpu` FROM `temporary_grouped_data` ORDER BY `cpu` ASC LIMIT 1726, 1;
SELECT `mu` FROM `temporary_grouped_data` ORDER BY `mu` ASC LIMIT 1726, 1;
SELECT `pmu` FROM `temporary_grouped_data` ORDER BY `pmu` ASC LIMIT 1726, 1;
4)计算模式(200ms)
SELECT `wt`, COUNT(`wt`) `quantity` FROM `temporary_grouped_data` GROUP BY `wt` ORDER BY `quantity` DESC LIMIT 1;
SELECT `cpu`, COUNT(`cpu`) `quantity` FROM `temporary_grouped_data` GROUP BY `cpu` ORDER BY `quantity` DESC LIMIT 1;
SELECT `mu`, COUNT(`mu`) `quantity` FROM `temporary_grouped_data` GROUP BY `mu` ORDER BY `quantity` DESC LIMIT 1;
SELECT `pmu`, COUNT(`pmu`) `quantity` FROM `temporary_grouped_data` GROUP BY `pmu` ORDER BY `quantity` DESC LIMIT 1
PHP方式。
1)将所有相关记录放入一个数组中(200ms)。
SELECT
`r1`.`id`,
`c1`.`wt`,
`c1`.`cpu`,
`c1`.`mu`,
`c1`.`pmu`
FROM
`requests` `r1`
INNER JOIN
`request_hosts` `rh1`
ON
`rh1`.`id` = `r1`.`request_host_id`
INNER JOIN
`request_uris` `ru1`
ON
`ru1`.`id` = `r1`.`request_uri_id`
INNER JOIN
`calls` `c1`
ON
`c1`.`id` = `r1`.`request_caller_id`
2) 执行所有计算(200 毫秒)。
PHP 方法要快得多。我有什么理由不应该使用 PHP 来执行这些计算?