如何减少单个查询中的冗余 MySQL 函数调用?
How to reduce redundant MySQL function calls in a single query?
SELECT hour(datetime), COUNT(animal_id)
FROM animal_outs
WHERE hour(datetime) > 8 AND hour(datetime) < 20
GROUP BY hour(datetime)
我正在学习SQL。我在查询中调用了四次 hour(datetime)
。我很好奇 1) 这种冗余是否会影响性能,以及 2) 如何简化这种冗余代码。
如果小时列有整数值那么试试这个one.We可以只删除一次冗余。
SELECT hour
,COUNT(animal_id)
FROM animal_outs
WHERE hour BETWEEN 8
AND 20
GROUP BY hour
如果小时是日期格式,请尝试以下代码。
SELECT DATEPART(HH,hour)
,COUNT(animal_id)
FROM animal_outs
WHERE DATEPART(HH,hour) BETWEEN 8
AND 20
GROUP BY DATEPART(HH,hour)
Does this affect performance?
可能没有任何意义。查询的性能通常取决于为检索和处理数据所做的工作。这通常比内置函数的开销要昂贵得多(尽管有一些例外,例如可能相当昂贵的正则表达式)。
MySQL 允许在 GROUP BY
中使用列别名。所以一个有效的 "simplification" 是:
SELECT hour(datetime) as hh, COUNT(animal_id)
FROM animal_outs
WHERE hour(datetime) > 8 AND hour(datetime) < 20
GROUP BY hh;
可能会使事情变得更糟的两个版本可能看起来对您来说更简单,但事实并非如此。第一种是使用 having
:
SELECT hour(datetime) as hh, COUNT(animal_id)
FROM animal_outs
GROUP BY hh
HAVING hh > 8 AND hh < 20
从技术上讲,这可以满足您的需求。但是因为它在 聚合之后过滤 ,所以它在 GROUP BY
上做额外的工作。这可能超过不打电话给 hour()
.
节省的任何费用
另一种方法是子查询:
SELECT hh, COUNT(animal_id)
FROM (SELECT hour(datetime) as hh, animal_id
FROM animal_outs
) ao
WHERE hh > 8 AND hh < 20
GROUP BY hh;
在大多数数据库中,这会满足您的要求。它 可能 在 MySQL 的最新版本中。但是,MySQL 在 FROM
子句中有一种令人讨厌的实现(即写入磁盘)子查询的趋势。这增加了额外的开销——再一次,可能比对 hour()
.
的额外调用更多
注意:hour()
可能是一个非常昂贵的函数,您可能会发现最后两个解决方案中的任何一个都更快。此外,如果您的数据至少有几千行,您可能只会看到对性能的影响。无论这些问题如何,通常都可以快速处理非常小的表(几十或几百行)。
SELECT hour(datetime), COUNT(animal_id)
FROM animal_outs
WHERE hour(datetime) > 8 AND hour(datetime) < 20
GROUP BY hour(datetime)
我正在学习SQL。我在查询中调用了四次 hour(datetime)
。我很好奇 1) 这种冗余是否会影响性能,以及 2) 如何简化这种冗余代码。
如果小时列有整数值那么试试这个one.We可以只删除一次冗余。
SELECT hour ,COUNT(animal_id) FROM animal_outs WHERE hour BETWEEN 8 AND 20 GROUP BY hour
如果小时是日期格式,请尝试以下代码。
SELECT DATEPART(HH,hour)
,COUNT(animal_id)
FROM animal_outs
WHERE DATEPART(HH,hour) BETWEEN 8
AND 20
GROUP BY DATEPART(HH,hour)
Does this affect performance?
可能没有任何意义。查询的性能通常取决于为检索和处理数据所做的工作。这通常比内置函数的开销要昂贵得多(尽管有一些例外,例如可能相当昂贵的正则表达式)。
MySQL 允许在 GROUP BY
中使用列别名。所以一个有效的 "simplification" 是:
SELECT hour(datetime) as hh, COUNT(animal_id)
FROM animal_outs
WHERE hour(datetime) > 8 AND hour(datetime) < 20
GROUP BY hh;
可能会使事情变得更糟的两个版本可能看起来对您来说更简单,但事实并非如此。第一种是使用 having
:
SELECT hour(datetime) as hh, COUNT(animal_id)
FROM animal_outs
GROUP BY hh
HAVING hh > 8 AND hh < 20
从技术上讲,这可以满足您的需求。但是因为它在 聚合之后过滤 ,所以它在 GROUP BY
上做额外的工作。这可能超过不打电话给 hour()
.
另一种方法是子查询:
SELECT hh, COUNT(animal_id)
FROM (SELECT hour(datetime) as hh, animal_id
FROM animal_outs
) ao
WHERE hh > 8 AND hh < 20
GROUP BY hh;
在大多数数据库中,这会满足您的要求。它 可能 在 MySQL 的最新版本中。但是,MySQL 在 FROM
子句中有一种令人讨厌的实现(即写入磁盘)子查询的趋势。这增加了额外的开销——再一次,可能比对 hour()
.
注意:hour()
可能是一个非常昂贵的函数,您可能会发现最后两个解决方案中的任何一个都更快。此外,如果您的数据至少有几千行,您可能只会看到对性能的影响。无论这些问题如何,通常都可以快速处理非常小的表(几十或几百行)。