我花了很长时间来学习如何在 MySQL 中处理时间戳,我认为我实现了我的目标,但我想仔细检查两件事:
1)这些是否符合我的预期
2)这些查询/功能是否有更快的替代品
今天
SELECT COUNT(*) AS count FROM log WHERE DATE(datet) = DATE(NOW())
Run Code Online (Sandbox Code Playgroud)
本星期
SELECT COUNT(*) AS count FROM log WHERE YEARWEEK(NOW()) = YEARWEEK(datet)
Run Code Online (Sandbox Code Playgroud)
上个星期
SELECT COUNT(*) AS count FROM log WHERE YEARWEEK(datet) = YEARWEEK(DATE_SUB(NOW(), INTERVAL 1 WEEK))
Run Code Online (Sandbox Code Playgroud)
这个月
SELECT COUNT(*) AS count FROM log WHERE datet > DATE_SUB(NOW(), INTERVAL 1 MONTH)
Run Code Online (Sandbox Code Playgroud)
上个月
SELECT COUNT(*) AS count FROM log WHERE datet > DATE_SUB(NOW(), INTERVAL 2 MONTH) AND datet < DATE_SUB(NOW(), INTERVAL 1 MONTH)
Run Code Online (Sandbox Code Playgroud)
小智 10
由于 MySQL 必须评估表中每一行的函数输出,因此将datet
列包装在函数中的查询效率不高(例如DATE()
, YEARWEEK()
)。这将查询呈现为不可 sargable(即无法利用datet
列上的索引)。
您似乎想要选择特定时间范围内所有记录的计数。为此,您必须使用>=
,而不是=
。此外,还有“之间的差异这个月”和“一个月内”。我假设你想要前者(即如果说今天是 8 月 3 日,你只想要 8 月内的记录,而不是从 7 月 3 日开始,以及一周的同样的事情,等等......)。
假设datet
是一个DATETIME
/TIMESTAMP
列并且该列的值永远不会“在未来”,您可以像这样重写您的查询(每个查询都可以使用该datet
列上的索引):
-- Today
SELECT COUNT(*) AS count
FROM log
WHERE datet >= CURDATE()
Run Code Online (Sandbox Code Playgroud)
-- This Week
SELECT COUNT(*) AS count
FROM log
WHERE datet >= CURDATE() - INTERVAL CASE WEEKDAY(CURDATE()) WHEN 6 THEN -1 ELSE WEEKDAY(CURDATE()) END + 1 DAY
Run Code Online (Sandbox Code Playgroud)
-- Last Week
SELECT COUNT(*) AS count
FROM log
WHERE datet >= (CURDATE() - INTERVAL CASE WEEKDAY(CURDATE()) WHEN 6 THEN -1 ELSE WEEKDAY(CURDATE()) END + 1 DAY) - INTERVAL 1 WEEK
AND
datet < CURDATE() - INTERVAL CASE WEEKDAY(CURDATE()) WHEN 6 THEN -1 ELSE WEEKDAY(CURDATE()) END + 1 DAY
Run Code Online (Sandbox Code Playgroud)
-- This Month
SELECT COUNT(*) AS count
FROM log
WHERE datet >= CURDATE() - INTERVAL DAYOFMONTH(CURDATE()) - 1 DAY
Run Code Online (Sandbox Code Playgroud)
-- Last Month
SELECT COUNT(*) AS count
FROM log
WHERE datet >= (CURDATE() - INTERVAL DAYOFMONTH(CURDATE()) - 1 DAY) - INTERVAL 1 MONTH
AND
datet < CURDATE() - INTERVAL DAYOFMONTH(CURDATE()) - 1 DAY
Run Code Online (Sandbox Code Playgroud)
-- This Year
SELECT COUNT(*) AS count
FROM log
WHERE datet >= MAKEDATE(YEAR(CURDATE()), 1)
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
2241 次 |
最近记录: |